Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(137)

Side by Side Diff: runtime/vm/intermediate_language_arm64.cc

Issue 2895183002: More compact string representation on 64 bit. (Closed)
Patch Set: Created 3 years, 7 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « runtime/vm/globals.h ('k') | runtime/vm/intermediate_language_x64.cc » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2014, the Dart project authors. Please see the AUTHORS file 1 // Copyright (c) 2014, the Dart project authors. Please see the AUTHORS file
2 // for details. All rights reserved. Use of this source code is governed by a 2 // for details. All rights reserved. Use of this source code is governed by a
3 // BSD-style license that can be found in the LICENSE file. 3 // BSD-style license that can be found in the LICENSE file.
4 4
5 #include "vm/globals.h" // Needed here to get TARGET_ARCH_ARM64. 5 #include "vm/globals.h" // Needed here to get TARGET_ARCH_ARM64.
6 #if defined(TARGET_ARCH_ARM64) 6 #if defined(TARGET_ARCH_ARM64)
7 7
8 #include "vm/intermediate_language.h" 8 #include "vm/intermediate_language.h"
9 9
10 #include "vm/compiler.h" 10 #include "vm/compiler.h"
(...skipping 1530 matching lines...) Expand 10 before | Expand all | Expand 10 after
1541 1541
1542 for (intptr_t i = 0; i < num_temps; i++) { 1542 for (intptr_t i = 0; i < num_temps; i++) {
1543 summary->set_temp(i, Location::RequiresRegister()); 1543 summary->set_temp(i, Location::RequiresRegister());
1544 } 1544 }
1545 1545
1546 return summary; 1546 return summary;
1547 } 1547 }
1548 1548
1549 1549
1550 void GuardFieldClassInstr::EmitNativeCode(FlowGraphCompiler* compiler) { 1550 void GuardFieldClassInstr::EmitNativeCode(FlowGraphCompiler* compiler) {
1551 ASSERT(sizeof(classid_t) == kInt32Size); 1551 ASSERT(sizeof(classid_t) == kInt16Size);
1552 const intptr_t value_cid = value()->Type()->ToCid(); 1552 const intptr_t value_cid = value()->Type()->ToCid();
1553 const intptr_t field_cid = field().guarded_cid(); 1553 const intptr_t field_cid = field().guarded_cid();
1554 const intptr_t nullability = field().is_nullable() ? kNullCid : kIllegalCid; 1554 const intptr_t nullability = field().is_nullable() ? kNullCid : kIllegalCid;
1555 1555
1556 if (field_cid == kDynamicCid) { 1556 if (field_cid == kDynamicCid) {
1557 if (Compiler::IsBackgroundCompilation()) { 1557 if (Compiler::IsBackgroundCompilation()) {
1558 // Field state changed while compiling. 1558 // Field state changed while compiling.
1559 Compiler::AbortBackgroundCompilation( 1559 Compiler::AbortBackgroundCompilation(
1560 deopt_id(), 1560 deopt_id(),
1561 "GuardFieldClassInstr: field state changed while compiling"); 1561 "GuardFieldClassInstr: field state changed while compiling");
(...skipping 25 matching lines...) Expand all
1587 compiler->is_optimizing() 1587 compiler->is_optimizing()
1588 ? compiler->AddDeoptStub(deopt_id(), ICData::kDeoptGuardField) 1588 ? compiler->AddDeoptStub(deopt_id(), ICData::kDeoptGuardField)
1589 : NULL; 1589 : NULL;
1590 1590
1591 Label* fail = (deopt != NULL) ? deopt : &fail_label; 1591 Label* fail = (deopt != NULL) ? deopt : &fail_label;
1592 1592
1593 if (emit_full_guard) { 1593 if (emit_full_guard) {
1594 __ LoadObject(field_reg, Field::ZoneHandle(field().Original())); 1594 __ LoadObject(field_reg, Field::ZoneHandle(field().Original()));
1595 1595
1596 FieldAddress field_cid_operand(field_reg, Field::guarded_cid_offset(), 1596 FieldAddress field_cid_operand(field_reg, Field::guarded_cid_offset(),
1597 kUnsignedWord); 1597 kUnsignedHalfword);
1598 FieldAddress field_nullability_operand( 1598 FieldAddress field_nullability_operand(
1599 field_reg, Field::is_nullable_offset(), kUnsignedWord); 1599 field_reg, Field::is_nullable_offset(), kUnsignedHalfword);
1600 1600
1601 if (value_cid == kDynamicCid) { 1601 if (value_cid == kDynamicCid) {
1602 LoadValueCid(compiler, value_cid_reg, value_reg); 1602 LoadValueCid(compiler, value_cid_reg, value_reg);
1603 Label skip_length_check; 1603 Label skip_length_check;
1604 __ ldr(TMP, field_cid_operand, kUnsignedWord); 1604 __ ldr(TMP, field_cid_operand, kUnsignedHalfword);
1605 __ CompareRegisters(value_cid_reg, TMP); 1605 __ CompareRegisters(value_cid_reg, TMP);
1606 __ b(&ok, EQ); 1606 __ b(&ok, EQ);
1607 __ ldr(TMP, field_nullability_operand, kUnsignedWord); 1607 __ ldr(TMP, field_nullability_operand, kUnsignedHalfword);
1608 __ CompareRegisters(value_cid_reg, TMP); 1608 __ CompareRegisters(value_cid_reg, TMP);
1609 } else if (value_cid == kNullCid) { 1609 } else if (value_cid == kNullCid) {
1610 __ ldr(value_cid_reg, field_nullability_operand, kUnsignedWord); 1610 __ ldr(value_cid_reg, field_nullability_operand, kUnsignedHalfword);
1611 __ CompareImmediate(value_cid_reg, value_cid); 1611 __ CompareImmediate(value_cid_reg, value_cid);
1612 } else { 1612 } else {
1613 Label skip_length_check; 1613 Label skip_length_check;
1614 __ ldr(value_cid_reg, field_cid_operand, kUnsignedWord); 1614 __ ldr(value_cid_reg, field_cid_operand, kUnsignedHalfword);
1615 __ CompareImmediate(value_cid_reg, value_cid); 1615 __ CompareImmediate(value_cid_reg, value_cid);
1616 } 1616 }
1617 __ b(&ok, EQ); 1617 __ b(&ok, EQ);
1618 1618
1619 // Check if the tracked state of the guarded field can be initialized 1619 // Check if the tracked state of the guarded field can be initialized
1620 // inline. If the field needs length check we fall through to runtime 1620 // inline. If the field needs length check we fall through to runtime
1621 // which is responsible for computing offset of the length field 1621 // which is responsible for computing offset of the length field
1622 // based on the class id. 1622 // based on the class id.
1623 // Length guard will be emitted separately when needed via GuardFieldLength 1623 // Length guard will be emitted separately when needed via GuardFieldLength
1624 // instruction after GuardFieldClass. 1624 // instruction after GuardFieldClass.
1625 if (!field().needs_length_check()) { 1625 if (!field().needs_length_check()) {
1626 // Uninitialized field can be handled inline. Check if the 1626 // Uninitialized field can be handled inline. Check if the
1627 // field is still unitialized. 1627 // field is still unitialized.
1628 __ ldr(TMP, field_cid_operand, kUnsignedWord); 1628 __ ldr(TMP, field_cid_operand, kUnsignedHalfword);
1629 __ CompareImmediate(TMP, kIllegalCid); 1629 __ CompareImmediate(TMP, kIllegalCid);
1630 __ b(fail, NE); 1630 __ b(fail, NE);
1631 1631
1632 if (value_cid == kDynamicCid) { 1632 if (value_cid == kDynamicCid) {
1633 __ str(value_cid_reg, field_cid_operand, kUnsignedWord); 1633 __ str(value_cid_reg, field_cid_operand, kUnsignedHalfword);
1634 __ str(value_cid_reg, field_nullability_operand, kUnsignedWord); 1634 __ str(value_cid_reg, field_nullability_operand, kUnsignedHalfword);
1635 } else { 1635 } else {
1636 __ LoadImmediate(TMP, value_cid); 1636 __ LoadImmediate(TMP, value_cid);
1637 __ str(TMP, field_cid_operand, kUnsignedWord); 1637 __ str(TMP, field_cid_operand, kUnsignedHalfword);
1638 __ str(TMP, field_nullability_operand, kUnsignedWord); 1638 __ str(TMP, field_nullability_operand, kUnsignedHalfword);
1639 } 1639 }
1640 1640
1641 if (deopt == NULL) { 1641 if (deopt == NULL) {
1642 ASSERT(!compiler->is_optimizing()); 1642 ASSERT(!compiler->is_optimizing());
1643 __ b(&ok); 1643 __ b(&ok);
1644 } 1644 }
1645 } 1645 }
1646 1646
1647 if (deopt == NULL) { 1647 if (deopt == NULL) {
1648 ASSERT(!compiler->is_optimizing()); 1648 ASSERT(!compiler->is_optimizing());
1649 __ Bind(fail); 1649 __ Bind(fail);
1650 1650
1651 __ LoadFieldFromOffset(TMP, field_reg, Field::guarded_cid_offset(), 1651 __ LoadFieldFromOffset(TMP, field_reg, Field::guarded_cid_offset(),
1652 kUnsignedWord); 1652 kUnsignedHalfword);
1653 __ CompareImmediate(TMP, kDynamicCid); 1653 __ CompareImmediate(TMP, kDynamicCid);
1654 __ b(&ok, EQ); 1654 __ b(&ok, EQ);
1655 1655
1656 __ Push(field_reg); 1656 __ Push(field_reg);
1657 __ Push(value_reg); 1657 __ Push(value_reg);
1658 __ CallRuntime(kUpdateFieldCidRuntimeEntry, 2); 1658 __ CallRuntime(kUpdateFieldCidRuntimeEntry, 2);
1659 __ Drop(2); // Drop the field and the value. 1659 __ Drop(2); // Drop the field and the value.
1660 } 1660 }
1661 } else { 1661 } else {
1662 ASSERT(compiler->is_optimizing()); 1662 ASSERT(compiler->is_optimizing());
(...skipping 218 matching lines...) Expand 10 before | Expand all | Expand 10 after
1881 } else { 1881 } else {
1882 summary->set_in(1, ShouldEmitStoreBarrier() 1882 summary->set_in(1, ShouldEmitStoreBarrier()
1883 ? Location::WritableRegister() 1883 ? Location::WritableRegister()
1884 : Location::RegisterOrConstant(value())); 1884 : Location::RegisterOrConstant(value()));
1885 } 1885 }
1886 return summary; 1886 return summary;
1887 } 1887 }
1888 1888
1889 1889
1890 void StoreInstanceFieldInstr::EmitNativeCode(FlowGraphCompiler* compiler) { 1890 void StoreInstanceFieldInstr::EmitNativeCode(FlowGraphCompiler* compiler) {
1891 ASSERT(sizeof(classid_t) == kInt32Size); 1891 ASSERT(sizeof(classid_t) == kInt16Size);
1892 Label skip_store; 1892 Label skip_store;
1893 1893
1894 const Register instance_reg = locs()->in(0).reg(); 1894 const Register instance_reg = locs()->in(0).reg();
1895 1895
1896 if (IsUnboxedStore() && compiler->is_optimizing()) { 1896 if (IsUnboxedStore() && compiler->is_optimizing()) {
1897 const VRegister value = locs()->in(1).fpu_reg(); 1897 const VRegister value = locs()->in(1).fpu_reg();
1898 const Register temp = locs()->temp(0).reg(); 1898 const Register temp = locs()->temp(0).reg();
1899 const Register temp2 = locs()->temp(1).reg(); 1899 const Register temp2 = locs()->temp(1).reg();
1900 const intptr_t cid = field().UnboxedFieldCid(); 1900 const intptr_t cid = field().UnboxedFieldCid();
1901 1901
(...skipping 51 matching lines...) Expand 10 before | Expand all | Expand 10 after
1953 } 1953 }
1954 1954
1955 Label store_pointer; 1955 Label store_pointer;
1956 Label store_double; 1956 Label store_double;
1957 Label store_float32x4; 1957 Label store_float32x4;
1958 Label store_float64x2; 1958 Label store_float64x2;
1959 1959
1960 __ LoadObject(temp, Field::ZoneHandle(Z, field().Original())); 1960 __ LoadObject(temp, Field::ZoneHandle(Z, field().Original()));
1961 1961
1962 __ LoadFieldFromOffset(temp2, temp, Field::is_nullable_offset(), 1962 __ LoadFieldFromOffset(temp2, temp, Field::is_nullable_offset(),
1963 kUnsignedWord); 1963 kUnsignedHalfword);
1964 __ CompareImmediate(temp2, kNullCid); 1964 __ CompareImmediate(temp2, kNullCid);
1965 __ b(&store_pointer, EQ); 1965 __ b(&store_pointer, EQ);
1966 1966
1967 __ LoadFromOffset(temp2, temp, Field::kind_bits_offset() - kHeapObjectTag, 1967 __ LoadFromOffset(temp2, temp, Field::kind_bits_offset() - kHeapObjectTag,
1968 kUnsignedByte); 1968 kUnsignedByte);
1969 __ tsti(temp2, Immediate(1 << Field::kUnboxingCandidateBit)); 1969 __ tsti(temp2, Immediate(1 << Field::kUnboxingCandidateBit));
1970 __ b(&store_pointer, EQ); 1970 __ b(&store_pointer, EQ);
1971 1971
1972 __ LoadFieldFromOffset(temp2, temp, Field::guarded_cid_offset(), 1972 __ LoadFieldFromOffset(temp2, temp, Field::guarded_cid_offset(),
1973 kUnsignedWord); 1973 kUnsignedHalfword);
1974 __ CompareImmediate(temp2, kDoubleCid); 1974 __ CompareImmediate(temp2, kDoubleCid);
1975 __ b(&store_double, EQ); 1975 __ b(&store_double, EQ);
1976 1976
1977 __ LoadFieldFromOffset(temp2, temp, Field::guarded_cid_offset(), 1977 __ LoadFieldFromOffset(temp2, temp, Field::guarded_cid_offset(),
1978 kUnsignedWord); 1978 kUnsignedHalfword);
1979 __ CompareImmediate(temp2, kFloat32x4Cid); 1979 __ CompareImmediate(temp2, kFloat32x4Cid);
1980 __ b(&store_float32x4, EQ); 1980 __ b(&store_float32x4, EQ);
1981 1981
1982 __ LoadFieldFromOffset(temp2, temp, Field::guarded_cid_offset(), 1982 __ LoadFieldFromOffset(temp2, temp, Field::guarded_cid_offset(),
1983 kUnsignedWord); 1983 kUnsignedHalfword);
1984 __ CompareImmediate(temp2, kFloat64x2Cid); 1984 __ CompareImmediate(temp2, kFloat64x2Cid);
1985 __ b(&store_float64x2, EQ); 1985 __ b(&store_float64x2, EQ);
1986 1986
1987 // Fall through. 1987 // Fall through.
1988 __ b(&store_pointer); 1988 __ b(&store_pointer);
1989 1989
1990 if (!compiler->is_optimizing()) { 1990 if (!compiler->is_optimizing()) {
1991 locs()->live_registers()->Add(locs()->in(0)); 1991 locs()->live_registers()->Add(locs()->in(0));
1992 locs()->live_registers()->Add(locs()->in(1)); 1992 locs()->live_registers()->Add(locs()->in(1));
1993 } 1993 }
(...skipping 243 matching lines...) Expand 10 before | Expand all | Expand 10 after
2237 locs->set_temp(0, Location::RequiresRegister()); 2237 locs->set_temp(0, Location::RequiresRegister());
2238 } else if (IsPotentialUnboxedLoad()) { 2238 } else if (IsPotentialUnboxedLoad()) {
2239 locs->set_temp(0, Location::RequiresRegister()); 2239 locs->set_temp(0, Location::RequiresRegister());
2240 } 2240 }
2241 locs->set_out(0, Location::RequiresRegister()); 2241 locs->set_out(0, Location::RequiresRegister());
2242 return locs; 2242 return locs;
2243 } 2243 }
2244 2244
2245 2245
2246 void LoadFieldInstr::EmitNativeCode(FlowGraphCompiler* compiler) { 2246 void LoadFieldInstr::EmitNativeCode(FlowGraphCompiler* compiler) {
2247 ASSERT(sizeof(classid_t) == kInt32Size); 2247 ASSERT(sizeof(classid_t) == kInt16Size);
2248 const Register instance_reg = locs()->in(0).reg(); 2248 const Register instance_reg = locs()->in(0).reg();
2249 if (IsUnboxedLoad() && compiler->is_optimizing()) { 2249 if (IsUnboxedLoad() && compiler->is_optimizing()) {
2250 const VRegister result = locs()->out(0).fpu_reg(); 2250 const VRegister result = locs()->out(0).fpu_reg();
2251 const Register temp = locs()->temp(0).reg(); 2251 const Register temp = locs()->temp(0).reg();
2252 __ LoadFieldFromOffset(temp, instance_reg, offset_in_bytes()); 2252 __ LoadFieldFromOffset(temp, instance_reg, offset_in_bytes());
2253 const intptr_t cid = field()->UnboxedFieldCid(); 2253 const intptr_t cid = field()->UnboxedFieldCid();
2254 switch (cid) { 2254 switch (cid) {
2255 case kDoubleCid: 2255 case kDoubleCid:
2256 __ Comment("UnboxedDoubleLoadFieldInstr"); 2256 __ Comment("UnboxedDoubleLoadFieldInstr");
2257 __ LoadDFieldFromOffset(result, temp, Double::value_offset()); 2257 __ LoadDFieldFromOffset(result, temp, Double::value_offset());
(...skipping 16 matching lines...) Expand all
2274 const Register temp = locs()->temp(0).reg(); 2274 const Register temp = locs()->temp(0).reg();
2275 2275
2276 Label load_pointer; 2276 Label load_pointer;
2277 Label load_double; 2277 Label load_double;
2278 Label load_float32x4; 2278 Label load_float32x4;
2279 Label load_float64x2; 2279 Label load_float64x2;
2280 2280
2281 __ LoadObject(result_reg, Field::ZoneHandle(field()->Original())); 2281 __ LoadObject(result_reg, Field::ZoneHandle(field()->Original()));
2282 2282
2283 FieldAddress field_cid_operand(result_reg, Field::guarded_cid_offset(), 2283 FieldAddress field_cid_operand(result_reg, Field::guarded_cid_offset(),
2284 kUnsignedWord); 2284 kUnsignedHalfword);
2285 FieldAddress field_nullability_operand( 2285 FieldAddress field_nullability_operand(
2286 result_reg, Field::is_nullable_offset(), kUnsignedWord); 2286 result_reg, Field::is_nullable_offset(), kUnsignedHalfword);
2287 2287
2288 __ ldr(temp, field_nullability_operand, kUnsignedWord); 2288 __ ldr(temp, field_nullability_operand, kUnsignedHalfword);
2289 __ CompareImmediate(temp, kNullCid); 2289 __ CompareImmediate(temp, kNullCid);
2290 __ b(&load_pointer, EQ); 2290 __ b(&load_pointer, EQ);
2291 2291
2292 __ ldr(temp, field_cid_operand, kUnsignedWord); 2292 __ ldr(temp, field_cid_operand, kUnsignedHalfword);
2293 __ CompareImmediate(temp, kDoubleCid); 2293 __ CompareImmediate(temp, kDoubleCid);
2294 __ b(&load_double, EQ); 2294 __ b(&load_double, EQ);
2295 2295
2296 __ ldr(temp, field_cid_operand, kUnsignedWord); 2296 __ ldr(temp, field_cid_operand, kUnsignedHalfword);
2297 __ CompareImmediate(temp, kFloat32x4Cid); 2297 __ CompareImmediate(temp, kFloat32x4Cid);
2298 __ b(&load_float32x4, EQ); 2298 __ b(&load_float32x4, EQ);
2299 2299
2300 __ ldr(temp, field_cid_operand, kUnsignedWord); 2300 __ ldr(temp, field_cid_operand, kUnsignedHalfword);
2301 __ CompareImmediate(temp, kFloat64x2Cid); 2301 __ CompareImmediate(temp, kFloat64x2Cid);
2302 __ b(&load_float64x2, EQ); 2302 __ b(&load_float64x2, EQ);
2303 2303
2304 // Fall through. 2304 // Fall through.
2305 __ b(&load_pointer); 2305 __ b(&load_pointer);
2306 2306
2307 if (!compiler->is_optimizing()) { 2307 if (!compiler->is_optimizing()) {
2308 locs()->live_registers()->Add(locs()->in(0)); 2308 locs()->live_registers()->Add(locs()->in(0));
2309 } 2309 }
2310 2310
(...skipping 3766 matching lines...) Expand 10 before | Expand all | Expand 10 after
6077 compiler->GenerateRuntimeCall(TokenPosition::kNoSource, deopt_id(), 6077 compiler->GenerateRuntimeCall(TokenPosition::kNoSource, deopt_id(),
6078 kGrowRegExpStackRuntimeEntry, 1, locs()); 6078 kGrowRegExpStackRuntimeEntry, 1, locs());
6079 __ Drop(1); 6079 __ Drop(1);
6080 __ Pop(result); 6080 __ Pop(result);
6081 } 6081 }
6082 6082
6083 6083
6084 } // namespace dart 6084 } // namespace dart
6085 6085
6086 #endif // defined TARGET_ARCH_ARM64 6086 #endif // defined TARGET_ARCH_ARM64
OLDNEW
« no previous file with comments | « runtime/vm/globals.h ('k') | runtime/vm/intermediate_language_x64.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698