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

Side by Side Diff: src/compiler/ia32/code-generator-ia32.cc

Issue 2170343002: [turbofan] Change Float64Max/Float64Min to JavaScript semantics. (Closed) Base URL: https://chromium.googlesource.com/v8/v8.git@master
Patch Set: mips/mips64 ports. Created 4 years, 5 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/compiler/common-operator-reducer.cc ('k') | src/compiler/ia32/instruction-codes-ia32.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 2013 the V8 project authors. All rights reserved. 1 // Copyright 2013 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/code-generator.h" 5 #include "src/compiler/code-generator.h"
6 6
7 #include "src/ast/scopes.h" 7 #include "src/ast/scopes.h"
8 #include "src/compiler/code-generator-impl.h" 8 #include "src/compiler/code-generator-impl.h"
9 #include "src/compiler/gap-resolver.h" 9 #include "src/compiler/gap-resolver.h"
10 #include "src/compiler/node-matchers.h" 10 #include "src/compiler/node-matchers.h"
(...skipping 179 matching lines...) Expand 10 before | Expand all | Expand 10 after
190 public: 190 public:
191 OutOfLineLoadInteger(CodeGenerator* gen, Register result) 191 OutOfLineLoadInteger(CodeGenerator* gen, Register result)
192 : OutOfLineCode(gen), result_(result) {} 192 : OutOfLineCode(gen), result_(result) {}
193 193
194 void Generate() final { __ xor_(result_, result_); } 194 void Generate() final { __ xor_(result_, result_); }
195 195
196 private: 196 private:
197 Register const result_; 197 Register const result_;
198 }; 198 };
199 199
200 200 class OutOfLineLoadNaN final : public OutOfLineCode {
201 class OutOfLineLoadFloat final : public OutOfLineCode {
202 public: 201 public:
203 OutOfLineLoadFloat(CodeGenerator* gen, XMMRegister result) 202 OutOfLineLoadNaN(CodeGenerator* gen, XMMRegister result)
204 : OutOfLineCode(gen), result_(result) {} 203 : OutOfLineCode(gen), result_(result) {}
205 204
206 void Generate() final { __ pcmpeqd(result_, result_); } 205 void Generate() final { __ pcmpeqd(result_, result_); }
207 206
208 private: 207 private:
209 XMMRegister const result_; 208 XMMRegister const result_;
210 }; 209 };
211 210
212 211
213 class OutOfLineTruncateDoubleToI final : public OutOfLineCode { 212 class OutOfLineTruncateDoubleToI final : public OutOfLineCode {
(...skipping 50 matching lines...) Expand 10 before | Expand all | Expand 10 after
264 Register const object_; 263 Register const object_;
265 Operand const operand_; 264 Operand const operand_;
266 Register const value_; 265 Register const value_;
267 Register const scratch0_; 266 Register const scratch0_;
268 Register const scratch1_; 267 Register const scratch1_;
269 RecordWriteMode const mode_; 268 RecordWriteMode const mode_;
270 }; 269 };
271 270
272 } // namespace 271 } // namespace
273 272
274 273 #define ASSEMBLE_CHECKED_LOAD_FLOAT(asm_instr) \
275 #define ASSEMBLE_CHECKED_LOAD_FLOAT(asm_instr) \ 274 do { \
276 do { \ 275 auto result = i.OutputDoubleRegister(); \
277 auto result = i.OutputDoubleRegister(); \ 276 auto offset = i.InputRegister(0); \
278 auto offset = i.InputRegister(0); \ 277 if (instr->InputAt(1)->IsRegister()) { \
279 if (instr->InputAt(1)->IsRegister()) { \ 278 __ cmp(offset, i.InputRegister(1)); \
280 __ cmp(offset, i.InputRegister(1)); \ 279 } else { \
281 } else { \ 280 __ cmp(offset, i.InputImmediate(1)); \
282 __ cmp(offset, i.InputImmediate(1)); \ 281 } \
283 } \ 282 OutOfLineCode* ool = new (zone()) OutOfLineLoadNaN(this, result); \
284 OutOfLineCode* ool = new (zone()) OutOfLineLoadFloat(this, result); \ 283 __ j(above_equal, ool->entry()); \
285 __ j(above_equal, ool->entry()); \ 284 __ asm_instr(result, i.MemoryOperand(2)); \
286 __ asm_instr(result, i.MemoryOperand(2)); \ 285 __ bind(ool->exit()); \
287 __ bind(ool->exit()); \
288 } while (false) 286 } while (false)
289 287
290
291 #define ASSEMBLE_CHECKED_LOAD_INTEGER(asm_instr) \ 288 #define ASSEMBLE_CHECKED_LOAD_INTEGER(asm_instr) \
292 do { \ 289 do { \
293 auto result = i.OutputRegister(); \ 290 auto result = i.OutputRegister(); \
294 auto offset = i.InputRegister(0); \ 291 auto offset = i.InputRegister(0); \
295 if (instr->InputAt(1)->IsRegister()) { \ 292 if (instr->InputAt(1)->IsRegister()) { \
296 __ cmp(offset, i.InputRegister(1)); \ 293 __ cmp(offset, i.InputRegister(1)); \
297 } else { \ 294 } else { \
298 __ cmp(offset, i.InputImmediate(1)); \ 295 __ cmp(offset, i.InputImmediate(1)); \
299 } \ 296 } \
300 OutOfLineCode* ool = new (zone()) OutOfLineLoadInteger(this, result); \ 297 OutOfLineCode* ool = new (zone()) OutOfLineLoadInteger(this, result); \
(...skipping 682 matching lines...) Expand 10 before | Expand all | Expand 10 after
983 break; 980 break;
984 case kSSEFloat32Mul: 981 case kSSEFloat32Mul:
985 __ mulss(i.InputDoubleRegister(0), i.InputOperand(1)); 982 __ mulss(i.InputDoubleRegister(0), i.InputOperand(1));
986 break; 983 break;
987 case kSSEFloat32Div: 984 case kSSEFloat32Div:
988 __ divss(i.InputDoubleRegister(0), i.InputOperand(1)); 985 __ divss(i.InputDoubleRegister(0), i.InputOperand(1));
989 // Don't delete this mov. It may improve performance on some CPUs, 986 // Don't delete this mov. It may improve performance on some CPUs,
990 // when there is a (v)mulss depending on the result. 987 // when there is a (v)mulss depending on the result.
991 __ movaps(i.OutputDoubleRegister(), i.OutputDoubleRegister()); 988 __ movaps(i.OutputDoubleRegister(), i.OutputDoubleRegister());
992 break; 989 break;
993 case kSSEFloat32Max:
994 __ maxss(i.InputDoubleRegister(0), i.InputOperand(1));
995 break;
996 case kSSEFloat32Min:
997 __ minss(i.InputDoubleRegister(0), i.InputOperand(1));
998 break;
999 case kSSEFloat32Sqrt: 990 case kSSEFloat32Sqrt:
1000 __ sqrtss(i.OutputDoubleRegister(), i.InputOperand(0)); 991 __ sqrtss(i.OutputDoubleRegister(), i.InputOperand(0));
1001 break; 992 break;
1002 case kSSEFloat32Abs: { 993 case kSSEFloat32Abs: {
1003 // TODO(bmeurer): Use 128-bit constants. 994 // TODO(bmeurer): Use 128-bit constants.
1004 __ pcmpeqd(kScratchDoubleReg, kScratchDoubleReg); 995 __ pcmpeqd(kScratchDoubleReg, kScratchDoubleReg);
1005 __ psrlq(kScratchDoubleReg, 33); 996 __ psrlq(kScratchDoubleReg, 33);
1006 __ andps(i.OutputDoubleRegister(), kScratchDoubleReg); 997 __ andps(i.OutputDoubleRegister(), kScratchDoubleReg);
1007 break; 998 break;
1008 } 999 }
(...skipping 22 matching lines...) Expand all
1031 break; 1022 break;
1032 case kSSEFloat64Mul: 1023 case kSSEFloat64Mul:
1033 __ mulsd(i.InputDoubleRegister(0), i.InputOperand(1)); 1024 __ mulsd(i.InputDoubleRegister(0), i.InputOperand(1));
1034 break; 1025 break;
1035 case kSSEFloat64Div: 1026 case kSSEFloat64Div:
1036 __ divsd(i.InputDoubleRegister(0), i.InputOperand(1)); 1027 __ divsd(i.InputDoubleRegister(0), i.InputOperand(1));
1037 // Don't delete this mov. It may improve performance on some CPUs, 1028 // Don't delete this mov. It may improve performance on some CPUs,
1038 // when there is a (v)mulsd depending on the result. 1029 // when there is a (v)mulsd depending on the result.
1039 __ movaps(i.OutputDoubleRegister(), i.OutputDoubleRegister()); 1030 __ movaps(i.OutputDoubleRegister(), i.OutputDoubleRegister());
1040 break; 1031 break;
1041 case kSSEFloat64Max: 1032 case kSSEFloat64Max: {
1042 __ maxsd(i.InputDoubleRegister(0), i.InputOperand(1)); 1033 Label compare_nan, compare_swap, done_compare;
1034 if (instr->InputAt(1)->IsFPRegister()) {
1035 __ ucomisd(i.InputDoubleRegister(0), i.InputDoubleRegister(1));
1036 } else {
1037 __ ucomisd(i.InputDoubleRegister(0), i.InputOperand(1));
1038 }
1039 auto ool = new (zone()) OutOfLineLoadNaN(this, i.OutputDoubleRegister());
1040 __ j(parity_even, ool->entry());
1041 __ j(above, &done_compare, Label::kNear);
1042 __ j(below, &compare_swap, Label::kNear);
1043 __ movmskpd(i.TempRegister(0), i.InputDoubleRegister(0));
1044 __ test(i.TempRegister(0), Immediate(1));
1045 __ j(zero, &done_compare, Label::kNear);
1046 __ bind(&compare_swap);
1047 if (instr->InputAt(1)->IsFPRegister()) {
1048 __ movsd(i.InputDoubleRegister(0), i.InputDoubleRegister(1));
1049 } else {
1050 __ movsd(i.InputDoubleRegister(0), i.InputOperand(1));
1051 }
1052 __ bind(&done_compare);
1053 __ bind(ool->exit());
1043 break; 1054 break;
1044 case kSSEFloat64Min: 1055 }
1045 __ minsd(i.InputDoubleRegister(0), i.InputOperand(1)); 1056 case kSSEFloat64Min: {
1057 Label compare_swap, done_compare;
1058 if (instr->InputAt(1)->IsFPRegister()) {
1059 __ ucomisd(i.InputDoubleRegister(0), i.InputDoubleRegister(1));
1060 } else {
1061 __ ucomisd(i.InputDoubleRegister(0), i.InputOperand(1));
1062 }
1063 auto ool = new (zone()) OutOfLineLoadNaN(this, i.OutputDoubleRegister());
1064 __ j(parity_even, ool->entry());
1065 __ j(below, &done_compare, Label::kNear);
1066 __ j(above, &compare_swap, Label::kNear);
1067 if (instr->InputAt(1)->IsFPRegister()) {
1068 __ movmskpd(i.TempRegister(0), i.InputDoubleRegister(1));
1069 } else {
1070 __ movsd(kScratchDoubleReg, i.InputOperand(1));
1071 __ movmskpd(i.TempRegister(0), kScratchDoubleReg);
1072 }
1073 __ test(i.TempRegister(0), Immediate(1));
1074 __ j(zero, &done_compare, Label::kNear);
1075 __ bind(&compare_swap);
1076 if (instr->InputAt(1)->IsFPRegister()) {
1077 __ movsd(i.InputDoubleRegister(0), i.InputDoubleRegister(1));
1078 } else {
1079 __ movsd(i.InputDoubleRegister(0), i.InputOperand(1));
1080 }
1081 __ bind(&done_compare);
1082 __ bind(ool->exit());
1046 break; 1083 break;
1084 }
1047 case kSSEFloat64Mod: { 1085 case kSSEFloat64Mod: {
1048 // TODO(dcarney): alignment is wrong. 1086 // TODO(dcarney): alignment is wrong.
1049 __ sub(esp, Immediate(kDoubleSize)); 1087 __ sub(esp, Immediate(kDoubleSize));
1050 // Move values to st(0) and st(1). 1088 // Move values to st(0) and st(1).
1051 __ movsd(Operand(esp, 0), i.InputDoubleRegister(1)); 1089 __ movsd(Operand(esp, 0), i.InputDoubleRegister(1));
1052 __ fld_d(Operand(esp, 0)); 1090 __ fld_d(Operand(esp, 0));
1053 __ movsd(Operand(esp, 0), i.InputDoubleRegister(0)); 1091 __ movsd(Operand(esp, 0), i.InputDoubleRegister(0));
1054 __ fld_d(Operand(esp, 0)); 1092 __ fld_d(Operand(esp, 0));
1055 // Loop while fprem isn't done. 1093 // Loop while fprem isn't done.
1056 Label mod_loop; 1094 Label mod_loop;
(...skipping 126 matching lines...) Expand 10 before | Expand all | Expand 10 after
1183 } 1221 }
1184 case kAVXFloat32Div: { 1222 case kAVXFloat32Div: {
1185 CpuFeatureScope avx_scope(masm(), AVX); 1223 CpuFeatureScope avx_scope(masm(), AVX);
1186 __ vdivss(i.OutputDoubleRegister(), i.InputDoubleRegister(0), 1224 __ vdivss(i.OutputDoubleRegister(), i.InputDoubleRegister(0),
1187 i.InputOperand(1)); 1225 i.InputOperand(1));
1188 // Don't delete this mov. It may improve performance on some CPUs, 1226 // Don't delete this mov. It may improve performance on some CPUs,
1189 // when there is a (v)mulss depending on the result. 1227 // when there is a (v)mulss depending on the result.
1190 __ movaps(i.OutputDoubleRegister(), i.OutputDoubleRegister()); 1228 __ movaps(i.OutputDoubleRegister(), i.OutputDoubleRegister());
1191 break; 1229 break;
1192 } 1230 }
1193 case kAVXFloat32Max: {
1194 CpuFeatureScope avx_scope(masm(), AVX);
1195 __ vmaxss(i.OutputDoubleRegister(), i.InputDoubleRegister(0),
1196 i.InputOperand(1));
1197 break;
1198 }
1199 case kAVXFloat32Min: {
1200 CpuFeatureScope avx_scope(masm(), AVX);
1201 __ vminss(i.OutputDoubleRegister(), i.InputDoubleRegister(0),
1202 i.InputOperand(1));
1203 break;
1204 }
1205 case kAVXFloat64Add: { 1231 case kAVXFloat64Add: {
1206 CpuFeatureScope avx_scope(masm(), AVX); 1232 CpuFeatureScope avx_scope(masm(), AVX);
1207 __ vaddsd(i.OutputDoubleRegister(), i.InputDoubleRegister(0), 1233 __ vaddsd(i.OutputDoubleRegister(), i.InputDoubleRegister(0),
1208 i.InputOperand(1)); 1234 i.InputOperand(1));
1209 break; 1235 break;
1210 } 1236 }
1211 case kAVXFloat64Sub: { 1237 case kAVXFloat64Sub: {
1212 CpuFeatureScope avx_scope(masm(), AVX); 1238 CpuFeatureScope avx_scope(masm(), AVX);
1213 __ vsubsd(i.OutputDoubleRegister(), i.InputDoubleRegister(0), 1239 __ vsubsd(i.OutputDoubleRegister(), i.InputDoubleRegister(0),
1214 i.InputOperand(1)); 1240 i.InputOperand(1));
1215 break; 1241 break;
1216 } 1242 }
1217 case kAVXFloat64Mul: { 1243 case kAVXFloat64Mul: {
1218 CpuFeatureScope avx_scope(masm(), AVX); 1244 CpuFeatureScope avx_scope(masm(), AVX);
1219 __ vmulsd(i.OutputDoubleRegister(), i.InputDoubleRegister(0), 1245 __ vmulsd(i.OutputDoubleRegister(), i.InputDoubleRegister(0),
1220 i.InputOperand(1)); 1246 i.InputOperand(1));
1221 break; 1247 break;
1222 } 1248 }
1223 case kAVXFloat64Div: { 1249 case kAVXFloat64Div: {
1224 CpuFeatureScope avx_scope(masm(), AVX); 1250 CpuFeatureScope avx_scope(masm(), AVX);
1225 __ vdivsd(i.OutputDoubleRegister(), i.InputDoubleRegister(0), 1251 __ vdivsd(i.OutputDoubleRegister(), i.InputDoubleRegister(0),
1226 i.InputOperand(1)); 1252 i.InputOperand(1));
1227 // Don't delete this mov. It may improve performance on some CPUs, 1253 // Don't delete this mov. It may improve performance on some CPUs,
1228 // when there is a (v)mulsd depending on the result. 1254 // when there is a (v)mulsd depending on the result.
1229 __ movaps(i.OutputDoubleRegister(), i.OutputDoubleRegister()); 1255 __ movaps(i.OutputDoubleRegister(), i.OutputDoubleRegister());
1230 break; 1256 break;
1231 } 1257 }
1232 case kAVXFloat64Max: {
1233 CpuFeatureScope avx_scope(masm(), AVX);
1234 __ vmaxsd(i.OutputDoubleRegister(), i.InputDoubleRegister(0),
1235 i.InputOperand(1));
1236 break;
1237 }
1238 case kAVXFloat64Min: {
1239 CpuFeatureScope avx_scope(masm(), AVX);
1240 __ vminsd(i.OutputDoubleRegister(), i.InputDoubleRegister(0),
1241 i.InputOperand(1));
1242 break;
1243 }
1244 case kAVXFloat32Abs: { 1258 case kAVXFloat32Abs: {
1245 // TODO(bmeurer): Use RIP relative 128-bit constants. 1259 // TODO(bmeurer): Use RIP relative 128-bit constants.
1246 __ pcmpeqd(kScratchDoubleReg, kScratchDoubleReg); 1260 __ pcmpeqd(kScratchDoubleReg, kScratchDoubleReg);
1247 __ psrlq(kScratchDoubleReg, 33); 1261 __ psrlq(kScratchDoubleReg, 33);
1248 CpuFeatureScope avx_scope(masm(), AVX); 1262 CpuFeatureScope avx_scope(masm(), AVX);
1249 __ vandps(i.OutputDoubleRegister(), kScratchDoubleReg, i.InputOperand(0)); 1263 __ vandps(i.OutputDoubleRegister(), kScratchDoubleReg, i.InputOperand(0));
1250 break; 1264 break;
1251 } 1265 }
1252 case kAVXFloat32Neg: { 1266 case kAVXFloat32Neg: {
1253 // TODO(bmeurer): Use RIP relative 128-bit constants. 1267 // TODO(bmeurer): Use RIP relative 128-bit constants.
(...skipping 923 matching lines...) Expand 10 before | Expand all | Expand 10 after
2177 int padding_size = last_lazy_deopt_pc_ + space_needed - current_pc; 2191 int padding_size = last_lazy_deopt_pc_ + space_needed - current_pc;
2178 __ Nop(padding_size); 2192 __ Nop(padding_size);
2179 } 2193 }
2180 } 2194 }
2181 2195
2182 #undef __ 2196 #undef __
2183 2197
2184 } // namespace compiler 2198 } // namespace compiler
2185 } // namespace internal 2199 } // namespace internal
2186 } // namespace v8 2200 } // namespace v8
OLDNEW
« no previous file with comments | « src/compiler/common-operator-reducer.cc ('k') | src/compiler/ia32/instruction-codes-ia32.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698