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

Side by Side Diff: src/x64/fast-codegen-x64.cc

Issue 594008: Initial implementation of fast path operation for bitwise OR. (Closed)
Patch Set: Fixed bug, added test. Created 10 years, 10 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 | « src/ia32/fast-codegen-ia32.cc ('k') | test/mjsunit/compiler/this-property-refs.js » ('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 2010 the V8 project authors. All rights reserved. 1 // Copyright 2010 the V8 project authors. All rights reserved.
2 // Redistribution and use in source and binary forms, with or without 2 // Redistribution and use in source and binary forms, with or without
3 // modification, are permitted provided that the following conditions are 3 // modification, are permitted provided that the following conditions are
4 // met: 4 // met:
5 // 5 //
6 // * Redistributions of source code must retain the above copyright 6 // * Redistributions of source code must retain the above copyright
7 // notice, this list of conditions and the following disclaimer. 7 // notice, this list of conditions and the following disclaimer.
8 // * Redistributions in binary form must reproduce the above 8 // * Redistributions in binary form must reproduce the above
9 // copyright notice, this list of conditions and the following 9 // copyright notice, this list of conditions and the following
10 // disclaimer in the documentation and/or other materials provided 10 // disclaimer in the documentation and/or other materials provided
(...skipping 17 matching lines...) Expand all
28 #include "v8.h" 28 #include "v8.h"
29 29
30 #include "codegen-inl.h" 30 #include "codegen-inl.h"
31 #include "fast-codegen.h" 31 #include "fast-codegen.h"
32 32
33 namespace v8 { 33 namespace v8 {
34 namespace internal { 34 namespace internal {
35 35
36 #define __ ACCESS_MASM(masm()) 36 #define __ ACCESS_MASM(masm())
37 37
38 // Registers rcx, rdi, and r8-r15 are free to use as scratch registers
39 // without saving and restoring any other registers.
40 Register FastCodeGenerator::accumulator0() { return rax; } 38 Register FastCodeGenerator::accumulator0() { return rax; }
41 Register FastCodeGenerator::accumulator1() { return rdx; } 39 Register FastCodeGenerator::accumulator1() { return rdx; }
42 Register FastCodeGenerator::scratch0() { return rcx; } 40 Register FastCodeGenerator::scratch0() { return rcx; }
43 Register FastCodeGenerator::scratch1() { return rdi; } 41 Register FastCodeGenerator::scratch1() { return rdi; }
44 Register FastCodeGenerator::receiver_reg() { return rbx; } 42 Register FastCodeGenerator::receiver_reg() { return rbx; }
45 Register FastCodeGenerator::context_reg() { return rsi; } 43 Register FastCodeGenerator::context_reg() { return rsi; }
46 44
47 45
48 void FastCodeGenerator::EmitLoadReceiver() { 46 void FastCodeGenerator::EmitLoadReceiver() {
49 // Offset 2 is due to return address and saved frame pointer. 47 // Offset 2 is due to return address and saved frame pointer.
50 int index = 2 + scope()->num_parameters(); 48 int index = 2 + scope()->num_parameters();
51 __ movq(receiver_reg(), Operand(rbp, index * kPointerSize)); 49 __ movq(receiver_reg(), Operand(rbp, index * kPointerSize));
52 } 50 }
53 51
54 52
55 void FastCodeGenerator::EmitGlobalVariableLoad(Handle<Object> cell) { 53 void FastCodeGenerator::EmitGlobalVariableLoad(Handle<Object> cell) {
54 ASSERT(!destination().is(no_reg));
56 ASSERT(cell->IsJSGlobalPropertyCell()); 55 ASSERT(cell->IsJSGlobalPropertyCell());
57 __ Move(accumulator0(), cell); 56 __ Move(destination(), cell);
58 __ movq(accumulator0(), 57 __ movq(destination(),
59 FieldOperand(accumulator0(), JSGlobalPropertyCell::kValueOffset)); 58 FieldOperand(destination(), JSGlobalPropertyCell::kValueOffset));
60 if (FLAG_debug_code) { 59 if (FLAG_debug_code) {
61 __ Cmp(accumulator0(), Factory::the_hole_value()); 60 __ Cmp(destination(), Factory::the_hole_value());
62 __ Check(not_equal, "DontDelete cells can't contain the hole"); 61 __ Check(not_equal, "DontDelete cells can't contain the hole");
63 } 62 }
64 } 63 }
65 64
66 65
67 void FastCodeGenerator::EmitThisPropertyStore(Handle<String> name) { 66 void FastCodeGenerator::EmitThisPropertyStore(Handle<String> name) {
68 LookupResult lookup; 67 LookupResult lookup;
69 info()->receiver()->Lookup(*name, &lookup); 68 info()->receiver()->Lookup(*name, &lookup);
70 69
71 ASSERT(lookup.holder() == *info()->receiver()); 70 ASSERT(lookup.holder() == *info()->receiver());
72 ASSERT(lookup.type() == FIELD); 71 ASSERT(lookup.type() == FIELD);
73 Handle<Map> map(Handle<HeapObject>::cast(info()->receiver())->map()); 72 Handle<Map> map(Handle<HeapObject>::cast(info()->receiver())->map());
74 int index = lookup.GetFieldIndex() - map->inobject_properties(); 73 int index = lookup.GetFieldIndex() - map->inobject_properties();
75 int offset = index * kPointerSize; 74 int offset = index * kPointerSize;
76 75
77 // Negative offsets are inobject properties. 76 // Negative offsets are inobject properties.
78 if (offset < 0) { 77 if (offset < 0) {
79 offset += map->instance_size(); 78 offset += map->instance_size();
80 __ movq(scratch0(), receiver_reg()); // Copy receiver for write barrier. 79 __ movq(scratch0(), receiver_reg()); // Copy receiver for write barrier.
81 } else { 80 } else {
82 offset += FixedArray::kHeaderSize; 81 offset += FixedArray::kHeaderSize;
83 __ movq(scratch0(), 82 __ movq(scratch0(),
84 FieldOperand(receiver_reg(), JSObject::kPropertiesOffset)); 83 FieldOperand(receiver_reg(), JSObject::kPropertiesOffset));
85 } 84 }
86 // Perform the store. 85 // Perform the store.
87 __ movq(FieldOperand(scratch0(), offset), accumulator0()); 86 __ movq(FieldOperand(scratch0(), offset), accumulator0());
88 // Preserve value from write barrier in case it's needed. 87 if (destination().is(no_reg)) {
89 __ movq(accumulator1(), accumulator0()); 88 __ RecordWrite(scratch0(), offset, accumulator0(), scratch1());
90 // The other accumulator register is available as a scratch register 89 } else {
91 // because this is not an AST leaf node. 90 // Copy the value to the other accumulator to preserve a copy from the
92 __ RecordWrite(scratch0(), offset, accumulator1(), scratch1()); 91 // write barrier. One of the accumulators is available as a scratch
92 // register.
93 __ movq(accumulator1(), accumulator0());
94 Register value_scratch = other_accumulator(destination());
95 __ RecordWrite(scratch0(), offset, value_scratch, scratch1());
96 }
93 } 97 }
94 98
95 99
100 void FastCodeGenerator::EmitThisPropertyLoad(Handle<String> name) {
101 ASSERT(!destination().is(no_reg));
102 LookupResult lookup;
103 info()->receiver()->Lookup(*name, &lookup);
104
105 ASSERT(lookup.holder() == *info()->receiver());
106 ASSERT(lookup.type() == FIELD);
107 Handle<Map> map(Handle<HeapObject>::cast(info()->receiver())->map());
108 int index = lookup.GetFieldIndex() - map->inobject_properties();
109 int offset = index * kPointerSize;
110
111 // Perform the load. Negative offsets are inobject properties.
112 if (offset < 0) {
113 offset += map->instance_size();
114 __ movq(destination(), FieldOperand(receiver_reg(), offset));
115 } else {
116 offset += FixedArray::kHeaderSize;
117 __ movq(scratch0(),
118 FieldOperand(receiver_reg(), JSObject::kPropertiesOffset));
119 __ movq(destination(), FieldOperand(scratch0(), offset));
120 }
121 }
122
123
124 void FastCodeGenerator::EmitBitOr() {
125 Register copied; // One operand is copied to a scratch register.
126 Register other; // The other is not modified by the operation.
127 Register check; // A register is used for the smi check/operation.
128 if (destination().is(no_reg)) {
129 copied = accumulator1(); // Arbitrary choice of operand to copy.
130 other = accumulator0();
131 check = scratch0(); // Do not clobber either operand register.
132 } else {
133 copied = destination();
134 other = other_accumulator(destination());
135 check = destination();
136 }
137 __ movq(scratch0(), copied);
138 __ or_(check, other);
139 // Restore the clobbered operand if necessary.
140 if (destination().is(no_reg)) {
141 __ JumpIfNotSmi(check, bailout());
142 } else {
143 Label done;
144 __ JumpIfSmi(check, &done);
145 __ movq(copied, scratch0());
146 __ jmp(bailout());
147 __ bind(&done);
148 }
149 }
150
151
96 void FastCodeGenerator::Generate(CompilationInfo* compilation_info) { 152 void FastCodeGenerator::Generate(CompilationInfo* compilation_info) {
97 ASSERT(info_ == NULL); 153 ASSERT(info_ == NULL);
98 info_ = compilation_info; 154 info_ = compilation_info;
99 155
100 // Save the caller's frame pointer and set up our own. 156 // Save the caller's frame pointer and set up our own.
101 Comment prologue_cmnt(masm(), ";; Prologue"); 157 Comment prologue_cmnt(masm(), ";; Prologue");
102 __ push(rbp); 158 __ push(rbp);
103 __ movq(rbp, rsp); 159 __ movq(rbp, rsp);
104 __ push(rsi); // Context. 160 __ push(rsi); // Context.
105 __ push(rdi); // Closure. 161 __ push(rdi); // Closure.
(...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after
144 __ ret((scope()->num_parameters() + 1) * kPointerSize); 200 __ ret((scope()->num_parameters() + 1) * kPointerSize);
145 201
146 __ bind(&bailout_); 202 __ bind(&bailout_);
147 } 203 }
148 204
149 205
150 #undef __ 206 #undef __
151 207
152 208
153 } } // namespace v8::internal 209 } } // namespace v8::internal
OLDNEW
« no previous file with comments | « src/ia32/fast-codegen-ia32.cc ('k') | test/mjsunit/compiler/this-property-refs.js » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698