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

Side by Side Diff: src/compiler/machine-operator-reducer.cc

Issue 763963002: [turbofan] Add checked load/store operators. (Closed) Base URL: https://chromium.googlesource.com/v8/v8.git@master
Patch Set: Reapply fix. Created 6 years 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/compiler/machine-operator-reducer.h ('k') | src/compiler/opcodes.h » ('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 2014 the V8 project authors. All rights reserved. 1 // Copyright 2014 the V8 project authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "src/compiler/machine-operator-reducer.h" 5 #include "src/compiler/machine-operator-reducer.h"
6 6
7 #include "src/base/bits.h" 7 #include "src/base/bits.h"
8 #include "src/base/division-by-constant.h" 8 #include "src/base/division-by-constant.h"
9 #include "src/codegen.h" 9 #include "src/codegen.h"
10 #include "src/compiler/diamond.h" 10 #include "src/compiler/diamond.h"
(...skipping 101 matching lines...) Expand 10 before | Expand all | Expand 10 after
112 } 112 }
113 return quotient; 113 return quotient;
114 } 114 }
115 115
116 116
117 // Perform constant folding and strength reduction on machine operators. 117 // Perform constant folding and strength reduction on machine operators.
118 Reduction MachineOperatorReducer::Reduce(Node* node) { 118 Reduction MachineOperatorReducer::Reduce(Node* node) {
119 switch (node->opcode()) { 119 switch (node->opcode()) {
120 case IrOpcode::kProjection: 120 case IrOpcode::kProjection:
121 return ReduceProjection(OpParameter<size_t>(node), node->InputAt(0)); 121 return ReduceProjection(OpParameter<size_t>(node), node->InputAt(0));
122 case IrOpcode::kWord32And: { 122 case IrOpcode::kWord32And:
123 Int32BinopMatcher m(node); 123 return ReduceWord32And(node);
124 if (m.right().Is(0)) return Replace(m.right().node()); // x & 0 => 0
125 if (m.right().Is(-1)) return Replace(m.left().node()); // x & -1 => x
126 if (m.IsFoldable()) { // K & K => K
127 return ReplaceInt32(m.left().Value() & m.right().Value());
128 }
129 if (m.LeftEqualsRight()) return Replace(m.left().node()); // x & x => x
130 if (m.left().IsWord32And() && m.right().HasValue()) {
131 Int32BinopMatcher mleft(m.left().node());
132 if (mleft.right().HasValue()) { // (x & K) & K => x & K
133 node->ReplaceInput(0, mleft.left().node());
134 node->ReplaceInput(
135 1, Int32Constant(m.right().Value() & mleft.right().Value()));
136 return Changed(node);
137 }
138 }
139 if (m.left().IsInt32Add() && m.right().IsNegativePowerOf2()) {
140 Int32BinopMatcher mleft(m.left().node());
141 if (mleft.right().HasValue() &&
142 (mleft.right().Value() & m.right().Value()) ==
143 mleft.right().Value()) {
144 // (x + K) & K => (x & K) + K
145 return Replace(graph()->NewNode(
146 machine()->Int32Add(),
147 graph()->NewNode(machine()->Word32And(), mleft.left().node(),
148 m.right().node()),
149 mleft.right().node()));
150 }
151 }
152 break;
153 }
154 case IrOpcode::kWord32Or: 124 case IrOpcode::kWord32Or:
155 return ReduceWord32Or(node); 125 return ReduceWord32Or(node);
156 case IrOpcode::kWord32Xor: { 126 case IrOpcode::kWord32Xor: {
157 Int32BinopMatcher m(node); 127 Int32BinopMatcher m(node);
158 if (m.right().Is(0)) return Replace(m.left().node()); // x ^ 0 => x 128 if (m.right().Is(0)) return Replace(m.left().node()); // x ^ 0 => x
159 if (m.IsFoldable()) { // K ^ K => K 129 if (m.IsFoldable()) { // K ^ K => K
160 return ReplaceInt32(m.left().Value() ^ m.right().Value()); 130 return ReplaceInt32(m.left().Value() ^ m.right().Value());
161 } 131 }
162 if (m.LeftEqualsRight()) return ReplaceInt32(0); // x ^ x => 0 132 if (m.LeftEqualsRight()) return ReplaceInt32(0); // x ^ x => 0
163 if (m.left().IsWord32Xor() && m.right().Is(-1)) { 133 if (m.left().IsWord32Xor() && m.right().Is(-1)) {
164 Int32BinopMatcher mleft(m.left().node()); 134 Int32BinopMatcher mleft(m.left().node());
165 if (mleft.right().Is(-1)) { // (x ^ -1) ^ -1 => x 135 if (mleft.right().Is(-1)) { // (x ^ -1) ^ -1 => x
166 return Replace(mleft.left().node()); 136 return Replace(mleft.left().node());
167 } 137 }
168 } 138 }
169 break; 139 break;
170 } 140 }
171 case IrOpcode::kWord32Shl: { 141 case IrOpcode::kWord32Shl:
172 Int32BinopMatcher m(node); 142 return ReduceWord32Shl(node);
173 if (m.right().Is(0)) return Replace(m.left().node()); // x << 0 => x
174 if (m.IsFoldable()) { // K << K => K
175 return ReplaceInt32(m.left().Value() << m.right().Value());
176 }
177 if (m.right().IsInRange(1, 31)) {
178 // (x >>> K) << K => x & ~(2^K - 1)
179 // (x >> K) << K => x & ~(2^K - 1)
180 if (m.left().IsWord32Sar() || m.left().IsWord32Shr()) {
181 Int32BinopMatcher mleft(m.left().node());
182 if (mleft.right().Is(m.right().Value())) {
183 node->set_op(machine()->Word32And());
184 node->ReplaceInput(0, mleft.left().node());
185 node->ReplaceInput(
186 1, Uint32Constant(~((1U << m.right().Value()) - 1U)));
187 return Changed(node);
188 }
189 }
190 }
191 return ReduceWord32Shifts(node);
192 }
193 case IrOpcode::kWord32Shr: { 143 case IrOpcode::kWord32Shr: {
194 Uint32BinopMatcher m(node); 144 Uint32BinopMatcher m(node);
195 if (m.right().Is(0)) return Replace(m.left().node()); // x >>> 0 => x 145 if (m.right().Is(0)) return Replace(m.left().node()); // x >>> 0 => x
196 if (m.IsFoldable()) { // K >>> K => K 146 if (m.IsFoldable()) { // K >>> K => K
197 return ReplaceInt32(m.left().Value() >> m.right().Value()); 147 return ReplaceInt32(m.left().Value() >> m.right().Value());
198 } 148 }
199 return ReduceWord32Shifts(node); 149 return ReduceWord32Shifts(node);
200 } 150 }
201 case IrOpcode::kWord32Sar: { 151 case IrOpcode::kWord32Sar: {
202 Int32BinopMatcher m(node); 152 Int32BinopMatcher m(node);
(...skipping 85 matching lines...) Expand 10 before | Expand all | Expand 10 after
288 } 238 }
289 if (m.right().Is(-1)) { // x * -1 => 0 - x 239 if (m.right().Is(-1)) { // x * -1 => 0 - x
290 node->set_op(machine()->Int32Sub()); 240 node->set_op(machine()->Int32Sub());
291 node->ReplaceInput(0, Int32Constant(0)); 241 node->ReplaceInput(0, Int32Constant(0));
292 node->ReplaceInput(1, m.left().node()); 242 node->ReplaceInput(1, m.left().node());
293 return Changed(node); 243 return Changed(node);
294 } 244 }
295 if (m.right().IsPowerOf2()) { // x * 2^n => x << n 245 if (m.right().IsPowerOf2()) { // x * 2^n => x << n
296 node->set_op(machine()->Word32Shl()); 246 node->set_op(machine()->Word32Shl());
297 node->ReplaceInput(1, Int32Constant(WhichPowerOf2(m.right().Value()))); 247 node->ReplaceInput(1, Int32Constant(WhichPowerOf2(m.right().Value())));
298 return Changed(node); 248 Reduction reduction = ReduceWord32Shl(node);
249 return reduction.Changed() ? reduction : Changed(node);
299 } 250 }
300 break; 251 break;
301 } 252 }
302 case IrOpcode::kInt32Div: 253 case IrOpcode::kInt32Div:
303 return ReduceInt32Div(node); 254 return ReduceInt32Div(node);
304 case IrOpcode::kUint32Div: 255 case IrOpcode::kUint32Div:
305 return ReduceUint32Div(node); 256 return ReduceUint32Div(node);
306 case IrOpcode::kInt32Mod: 257 case IrOpcode::kInt32Mod:
307 return ReduceInt32Mod(node); 258 return ReduceInt32Mod(node);
308 case IrOpcode::kUint32Mod: 259 case IrOpcode::kUint32Mod:
(...skipping 447 matching lines...) Expand 10 before | Expand all | Expand 10 after
756 break; 707 break;
757 } 708 }
758 return NoChange(); 709 return NoChange();
759 } 710 }
760 711
761 712
762 Reduction MachineOperatorReducer::ReduceWord32Shifts(Node* node) { 713 Reduction MachineOperatorReducer::ReduceWord32Shifts(Node* node) {
763 DCHECK((node->opcode() == IrOpcode::kWord32Shl) || 714 DCHECK((node->opcode() == IrOpcode::kWord32Shl) ||
764 (node->opcode() == IrOpcode::kWord32Shr) || 715 (node->opcode() == IrOpcode::kWord32Shr) ||
765 (node->opcode() == IrOpcode::kWord32Sar)); 716 (node->opcode() == IrOpcode::kWord32Sar));
766
767 if (machine()->Word32ShiftIsSafe()) { 717 if (machine()->Word32ShiftIsSafe()) {
768 // Remove the explicit 'and' with 0x1f if the shift provided by the machine 718 // Remove the explicit 'and' with 0x1f if the shift provided by the machine
769 // instruction matches that required by JavaScript. 719 // instruction matches that required by JavaScript.
770 Int32BinopMatcher m(node); 720 Int32BinopMatcher m(node);
771 if (m.right().IsWord32And()) { 721 if (m.right().IsWord32And()) {
772 Int32BinopMatcher mright(m.right().node()); 722 Int32BinopMatcher mright(m.right().node());
773 if (mright.right().Is(0x1f)) { 723 if (mright.right().Is(0x1f)) {
774 node->ReplaceInput(1, mright.left().node()); 724 node->ReplaceInput(1, mright.left().node());
775 return Changed(node); 725 return Changed(node);
776 } 726 }
777 } 727 }
778 } 728 }
779 return NoChange(); 729 return NoChange();
780 } 730 }
781 731
782 732
733 Reduction MachineOperatorReducer::ReduceWord32Shl(Node* node) {
734 DCHECK_EQ(IrOpcode::kWord32Shl, node->opcode());
735 Int32BinopMatcher m(node);
736 if (m.right().Is(0)) return Replace(m.left().node()); // x << 0 => x
737 if (m.IsFoldable()) { // K << K => K
738 return ReplaceInt32(m.left().Value() << m.right().Value());
739 }
740 if (m.right().IsInRange(1, 31)) {
741 // (x >>> K) << K => x & ~(2^K - 1)
742 // (x >> K) << K => x & ~(2^K - 1)
743 if (m.left().IsWord32Sar() || m.left().IsWord32Shr()) {
744 Int32BinopMatcher mleft(m.left().node());
745 if (mleft.right().Is(m.right().Value())) {
746 node->set_op(machine()->Word32And());
747 node->ReplaceInput(0, mleft.left().node());
748 node->ReplaceInput(1,
749 Uint32Constant(~((1U << m.right().Value()) - 1U)));
750 Reduction reduction = ReduceWord32And(node);
751 return reduction.Changed() ? reduction : Changed(node);
752 }
753 }
754 }
755 return ReduceWord32Shifts(node);
756 }
757
758
759 Reduction MachineOperatorReducer::ReduceWord32And(Node* node) {
760 DCHECK_EQ(IrOpcode::kWord32And, node->opcode());
761 Int32BinopMatcher m(node);
762 if (m.right().Is(0)) return Replace(m.right().node()); // x & 0 => 0
763 if (m.right().Is(-1)) return Replace(m.left().node()); // x & -1 => x
764 if (m.IsFoldable()) { // K & K => K
765 return ReplaceInt32(m.left().Value() & m.right().Value());
766 }
767 if (m.LeftEqualsRight()) return Replace(m.left().node()); // x & x => x
768 if (m.left().IsWord32And() && m.right().HasValue()) {
769 Int32BinopMatcher mleft(m.left().node());
770 if (mleft.right().HasValue()) { // (x & K) & K => x & K
771 node->ReplaceInput(0, mleft.left().node());
772 node->ReplaceInput(
773 1, Int32Constant(m.right().Value() & mleft.right().Value()));
774 Reduction reduction = ReduceWord32And(node);
775 return reduction.Changed() ? reduction : Changed(node);
776 }
777 }
778 if (m.left().IsInt32Add() && m.right().IsNegativePowerOf2()) {
779 Int32BinopMatcher mleft(m.left().node());
780 if (mleft.right().HasValue() &&
781 (mleft.right().Value() & m.right().Value()) == mleft.right().Value()) {
782 // (x + K) & K => (x & K) + K
783 return Replace(graph()->NewNode(
784 machine()->Int32Add(),
785 graph()->NewNode(machine()->Word32And(), mleft.left().node(),
786 m.right().node()),
787 mleft.right().node()));
788 }
789 }
790 return NoChange();
791 }
792
793
783 Reduction MachineOperatorReducer::ReduceWord32Or(Node* node) { 794 Reduction MachineOperatorReducer::ReduceWord32Or(Node* node) {
784 DCHECK(node->opcode() == IrOpcode::kWord32Or); 795 DCHECK_EQ(IrOpcode::kWord32Or, node->opcode());
785
786 Int32BinopMatcher m(node); 796 Int32BinopMatcher m(node);
787 if (m.right().Is(0)) return Replace(m.left().node()); // x | 0 => x 797 if (m.right().Is(0)) return Replace(m.left().node()); // x | 0 => x
788 if (m.right().Is(-1)) return Replace(m.right().node()); // x | -1 => -1 798 if (m.right().Is(-1)) return Replace(m.right().node()); // x | -1 => -1
789 if (m.IsFoldable()) { // K | K => K 799 if (m.IsFoldable()) { // K | K => K
790 return ReplaceInt32(m.left().Value() | m.right().Value()); 800 return ReplaceInt32(m.left().Value() | m.right().Value());
791 } 801 }
792 if (m.LeftEqualsRight()) return Replace(m.left().node()); // x | x => x 802 if (m.LeftEqualsRight()) return Replace(m.left().node()); // x | x => x
793 803
794 Node* shl = NULL; 804 Node* shl = NULL;
795 Node* shr = NULL; 805 Node* shr = NULL;
(...skipping 50 matching lines...) Expand 10 before | Expand all | Expand 10 after
846 MachineOperatorBuilder* MachineOperatorReducer::machine() const { 856 MachineOperatorBuilder* MachineOperatorReducer::machine() const {
847 return jsgraph()->machine(); 857 return jsgraph()->machine();
848 } 858 }
849 859
850 860
851 Graph* MachineOperatorReducer::graph() const { return jsgraph()->graph(); } 861 Graph* MachineOperatorReducer::graph() const { return jsgraph()->graph(); }
852 862
853 } // namespace compiler 863 } // namespace compiler
854 } // namespace internal 864 } // namespace internal
855 } // namespace v8 865 } // namespace v8
OLDNEW
« no previous file with comments | « src/compiler/machine-operator-reducer.h ('k') | src/compiler/opcodes.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698