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

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

Issue 2220313002: S390: Decouple Add/Sub/Neg to 32/64 Bit Op (Closed) Base URL: https://chromium.googlesource.com/v8/v8.git@master
Patch Set: Fix Neg32 to use lcr Created 4 years, 4 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 | « no previous file | src/compiler/s390/instruction-codes-s390.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 2015 the V8 project authors. All rights reserved. 1 // Copyright 2015 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 217 matching lines...) Expand 10 before | Expand all | Expand 10 after
228 return ge; 228 return ge;
229 case kSignedLessThanOrEqual: 229 case kSignedLessThanOrEqual:
230 case kUnsignedLessThanOrEqual: 230 case kUnsignedLessThanOrEqual:
231 return le; 231 return le;
232 case kSignedGreaterThan: 232 case kSignedGreaterThan:
233 case kUnsignedGreaterThan: 233 case kUnsignedGreaterThan:
234 return gt; 234 return gt;
235 case kOverflow: 235 case kOverflow:
236 // Overflow checked for AddP/SubP only. 236 // Overflow checked for AddP/SubP only.
237 switch (op) { 237 switch (op) {
238 #if V8_TARGET_ARCH_S390X 238 case kS390_Add32:
239 case kS390_Add: 239 case kS390_Add64:
240 case kS390_Sub: 240 case kS390_Sub32:
241 #endif 241 case kS390_Sub64:
242 case kS390_AddWithOverflow32: 242 return overflow;
243 case kS390_SubWithOverflow32:
244 return lt;
245 default: 243 default:
246 break; 244 break;
247 } 245 }
248 break; 246 break;
249 case kNotOverflow: 247 case kNotOverflow:
250 switch (op) { 248 switch (op) {
251 #if V8_TARGET_ARCH_S390X 249 case kS390_Add32:
252 case kS390_Add: 250 case kS390_Add64:
253 case kS390_Sub: 251 case kS390_Sub32:
254 #endif 252 case kS390_Sub64:
255 case kS390_AddWithOverflow32: 253 return nooverflow;
256 case kS390_SubWithOverflow32:
257 return ge;
258 default: 254 default:
259 break; 255 break;
260 } 256 }
261 break; 257 break;
262 default: 258 default:
263 break; 259 break;
264 } 260 }
265 UNREACHABLE(); 261 UNREACHABLE();
266 return kNoCondition; 262 return kNoCondition;
267 } 263 }
(...skipping 15 matching lines...) Expand all
283 do { \ 279 do { \
284 if (HasRegisterInput(instr, 1)) { \ 280 if (HasRegisterInput(instr, 1)) { \
285 __ asm_instr(i.OutputRegister(), i.InputRegister(0), \ 281 __ asm_instr(i.OutputRegister(), i.InputRegister(0), \
286 i.InputRegister(1)); \ 282 i.InputRegister(1)); \
287 } else { \ 283 } else { \
288 __ asm_instr(i.OutputRegister(), i.InputRegister(0), \ 284 __ asm_instr(i.OutputRegister(), i.InputRegister(0), \
289 i.InputImmediate(1)); \ 285 i.InputImmediate(1)); \
290 } \ 286 } \
291 } while (0) 287 } while (0)
292 288
293 #define ASSEMBLE_BINOP_INT(asm_instr_reg, asm_instr_imm) \
294 do { \
295 if (HasRegisterInput(instr, 1)) { \
296 __ asm_instr_reg(i.OutputRegister(), i.InputRegister(0), \
297 i.InputRegister(1)); \
298 } else { \
299 __ asm_instr_imm(i.OutputRegister(), i.InputRegister(0), \
300 i.InputInt32(1)); \
301 } \
302 } while (0)
303
304 #define ASSEMBLE_ADD_WITH_OVERFLOW() \
305 do { \
306 if (HasRegisterInput(instr, 1)) { \
307 __ AddAndCheckForOverflow(i.OutputRegister(), i.InputRegister(0), \
308 i.InputRegister(1), kScratchReg, r0); \
309 } else { \
310 __ AddAndCheckForOverflow(i.OutputRegister(), i.InputRegister(0), \
311 i.InputInt32(1), kScratchReg, r0); \
312 } \
313 } while (0)
314
315 #define ASSEMBLE_SUB_WITH_OVERFLOW() \
316 do { \
317 if (HasRegisterInput(instr, 1)) { \
318 __ SubAndCheckForOverflow(i.OutputRegister(), i.InputRegister(0), \
319 i.InputRegister(1), kScratchReg, r0); \
320 } else { \
321 __ AddAndCheckForOverflow(i.OutputRegister(), i.InputRegister(0), \
322 -i.InputInt32(1), kScratchReg, r0); \
323 } \
324 } while (0)
325
326 #if V8_TARGET_ARCH_S390X
327 #define ASSEMBLE_ADD_WITH_OVERFLOW32() \
328 do { \
329 ASSEMBLE_ADD_WITH_OVERFLOW(); \
330 __ LoadAndTestP_ExtendSrc(kScratchReg, kScratchReg); \
331 } while (0)
332
333 #define ASSEMBLE_SUB_WITH_OVERFLOW32() \
334 do { \
335 ASSEMBLE_SUB_WITH_OVERFLOW(); \
336 __ LoadAndTestP_ExtendSrc(kScratchReg, kScratchReg); \
337 } while (0)
338 #else
339 #define ASSEMBLE_ADD_WITH_OVERFLOW32 ASSEMBLE_ADD_WITH_OVERFLOW
340 #define ASSEMBLE_SUB_WITH_OVERFLOW32 ASSEMBLE_SUB_WITH_OVERFLOW
341 #endif
342
343 #define ASSEMBLE_COMPARE(cmp_instr, cmpl_instr) \ 289 #define ASSEMBLE_COMPARE(cmp_instr, cmpl_instr) \
344 do { \ 290 do { \
345 if (HasRegisterInput(instr, 1)) { \ 291 if (HasRegisterInput(instr, 1)) { \
346 if (i.CompareLogical()) { \ 292 if (i.CompareLogical()) { \
347 __ cmpl_instr(i.InputRegister(0), i.InputRegister(1)); \ 293 __ cmpl_instr(i.InputRegister(0), i.InputRegister(1)); \
348 } else { \ 294 } else { \
349 __ cmp_instr(i.InputRegister(0), i.InputRegister(1)); \ 295 __ cmp_instr(i.InputRegister(0), i.InputRegister(1)); \
350 } \ 296 } \
351 } else { \ 297 } else { \
352 if (i.CompareLogical()) { \ 298 if (i.CompareLogical()) { \
(...skipping 849 matching lines...) Expand 10 before | Expand all | Expand 10 after
1202 Operand(endBit), Operand(shiftAmount), true); 1148 Operand(endBit), Operand(shiftAmount), true);
1203 } else { 1149 } else {
1204 int shiftAmount = i.InputInt32(1); 1150 int shiftAmount = i.InputInt32(1);
1205 int clearBit = i.InputInt32(2); 1151 int clearBit = i.InputInt32(2);
1206 __ rllg(i.OutputRegister(), i.InputRegister(0), Operand(shiftAmount)); 1152 __ rllg(i.OutputRegister(), i.InputRegister(0), Operand(shiftAmount));
1207 __ srlg(i.OutputRegister(), i.OutputRegister(), Operand(clearBit)); 1153 __ srlg(i.OutputRegister(), i.OutputRegister(), Operand(clearBit));
1208 __ sllg(i.OutputRegister(), i.OutputRegister(), Operand(clearBit)); 1154 __ sllg(i.OutputRegister(), i.OutputRegister(), Operand(clearBit));
1209 } 1155 }
1210 break; 1156 break;
1211 #endif 1157 #endif
1212 case kS390_Add: 1158 case kS390_Add32:
1213 #if V8_TARGET_ARCH_S390X 1159 ASSEMBLE_BINOP(Add32);
1214 if (FlagsModeField::decode(instr->opcode()) != kFlags_none) { 1160 __ LoadW(i.OutputRegister(), i.OutputRegister());
1215 ASSEMBLE_ADD_WITH_OVERFLOW();
1216 } else {
1217 #endif
1218 ASSEMBLE_BINOP(AddP);
1219 #if V8_TARGET_ARCH_S390X
1220 }
1221 #endif
1222 break; 1161 break;
1223 case kS390_AddWithOverflow32: 1162 case kS390_Add64:
1224 ASSEMBLE_ADD_WITH_OVERFLOW32(); 1163 ASSEMBLE_BINOP(AddP);
1225 break; 1164 break;
1226 case kS390_AddFloat: 1165 case kS390_AddFloat:
1227 // Ensure we don't clobber right/InputReg(1) 1166 // Ensure we don't clobber right/InputReg(1)
1228 if (i.OutputDoubleRegister().is(i.InputDoubleRegister(1))) { 1167 if (i.OutputDoubleRegister().is(i.InputDoubleRegister(1))) {
1229 ASSEMBLE_FLOAT_UNOP(aebr); 1168 ASSEMBLE_FLOAT_UNOP(aebr);
1230 } else { 1169 } else {
1231 if (!i.OutputDoubleRegister().is(i.InputDoubleRegister(0))) 1170 if (!i.OutputDoubleRegister().is(i.InputDoubleRegister(0)))
1232 __ ldr(i.OutputDoubleRegister(), i.InputDoubleRegister(0)); 1171 __ ldr(i.OutputDoubleRegister(), i.InputDoubleRegister(0));
1233 __ aebr(i.OutputDoubleRegister(), i.InputDoubleRegister(1)); 1172 __ aebr(i.OutputDoubleRegister(), i.InputDoubleRegister(1));
1234 } 1173 }
1235 break; 1174 break;
1236 case kS390_AddDouble: 1175 case kS390_AddDouble:
1237 // Ensure we don't clobber right/InputReg(1) 1176 // Ensure we don't clobber right/InputReg(1)
1238 if (i.OutputDoubleRegister().is(i.InputDoubleRegister(1))) { 1177 if (i.OutputDoubleRegister().is(i.InputDoubleRegister(1))) {
1239 ASSEMBLE_FLOAT_UNOP(adbr); 1178 ASSEMBLE_FLOAT_UNOP(adbr);
1240 } else { 1179 } else {
1241 if (!i.OutputDoubleRegister().is(i.InputDoubleRegister(0))) 1180 if (!i.OutputDoubleRegister().is(i.InputDoubleRegister(0)))
1242 __ ldr(i.OutputDoubleRegister(), i.InputDoubleRegister(0)); 1181 __ ldr(i.OutputDoubleRegister(), i.InputDoubleRegister(0));
1243 __ adbr(i.OutputDoubleRegister(), i.InputDoubleRegister(1)); 1182 __ adbr(i.OutputDoubleRegister(), i.InputDoubleRegister(1));
1244 } 1183 }
1245 break; 1184 break;
1246 case kS390_Sub: 1185 case kS390_Sub32:
1247 #if V8_TARGET_ARCH_S390X 1186 ASSEMBLE_BINOP(Sub32);
1248 if (FlagsModeField::decode(instr->opcode()) != kFlags_none) { 1187 __ LoadW(i.OutputRegister(), i.OutputRegister());
1249 ASSEMBLE_SUB_WITH_OVERFLOW();
1250 } else {
1251 #endif
1252 ASSEMBLE_BINOP(SubP);
1253 #if V8_TARGET_ARCH_S390X
1254 }
1255 #endif
1256 break; 1188 break;
1257 case kS390_SubWithOverflow32: 1189 case kS390_Sub64:
1258 ASSEMBLE_SUB_WITH_OVERFLOW32(); 1190 ASSEMBLE_BINOP(SubP);
1259 break; 1191 break;
1260 case kS390_SubFloat: 1192 case kS390_SubFloat:
1261 // OutputDoubleReg() = i.InputDoubleRegister(0) - i.InputDoubleRegister(1) 1193 // OutputDoubleReg() = i.InputDoubleRegister(0) - i.InputDoubleRegister(1)
1262 if (i.OutputDoubleRegister().is(i.InputDoubleRegister(1))) { 1194 if (i.OutputDoubleRegister().is(i.InputDoubleRegister(1))) {
1263 __ ldr(kScratchDoubleReg, i.InputDoubleRegister(1)); 1195 __ ldr(kScratchDoubleReg, i.InputDoubleRegister(1));
1264 __ ldr(i.OutputDoubleRegister(), i.InputDoubleRegister(0)); 1196 __ ldr(i.OutputDoubleRegister(), i.InputDoubleRegister(0));
1265 __ sebr(i.OutputDoubleRegister(), kScratchDoubleReg); 1197 __ sebr(i.OutputDoubleRegister(), kScratchDoubleReg);
1266 } else { 1198 } else {
1267 if (!i.OutputDoubleRegister().is(i.InputDoubleRegister(0))) { 1199 if (!i.OutputDoubleRegister().is(i.InputDoubleRegister(0))) {
1268 __ ldr(i.OutputDoubleRegister(), i.InputDoubleRegister(0)); 1200 __ ldr(i.OutputDoubleRegister(), i.InputDoubleRegister(0));
(...skipping 210 matching lines...) Expand 10 before | Expand all | Expand 10 after
1479 break; 1411 break;
1480 case kIeee754Float64Log10: 1412 case kIeee754Float64Log10:
1481 ASSEMBLE_IEEE754_UNOP(log10); 1413 ASSEMBLE_IEEE754_UNOP(log10);
1482 break; 1414 break;
1483 case kIeee754Float64Pow: { 1415 case kIeee754Float64Pow: {
1484 MathPowStub stub(isolate(), MathPowStub::DOUBLE); 1416 MathPowStub stub(isolate(), MathPowStub::DOUBLE);
1485 __ CallStub(&stub); 1417 __ CallStub(&stub);
1486 __ Move(d1, d3); 1418 __ Move(d1, d3);
1487 break; 1419 break;
1488 } 1420 }
1489 case kS390_Neg: 1421 case kS390_Neg32:
1490 __ LoadComplementRR(i.OutputRegister(), i.InputRegister(0)); 1422 __ lcr(i.OutputRegister(), i.InputRegister(0));
1423 __ LoadW(i.OutputRegister(), i.OutputRegister());
1424 break;
1425 case kS390_Neg64:
1426 __ lcgr(i.OutputRegister(), i.InputRegister(0));
1491 break; 1427 break;
1492 case kS390_MaxDouble: 1428 case kS390_MaxDouble:
1493 ASSEMBLE_FLOAT_MAX(); 1429 ASSEMBLE_FLOAT_MAX();
1494 break; 1430 break;
1495 case kS390_MinDouble: 1431 case kS390_MinDouble:
1496 ASSEMBLE_FLOAT_MIN(); 1432 ASSEMBLE_FLOAT_MIN();
1497 break; 1433 break;
1498 case kS390_AbsDouble: 1434 case kS390_AbsDouble:
1499 __ lpdbr(i.OutputDoubleRegister(), i.InputDoubleRegister(0)); 1435 __ lpdbr(i.OutputDoubleRegister(), i.InputDoubleRegister(0));
1500 break; 1436 break;
(...skipping 512 matching lines...) Expand 10 before | Expand all | Expand 10 after
2013 } 1949 }
2014 1950
2015 void CodeGenerator::AssembleArchJump(RpoNumber target) { 1951 void CodeGenerator::AssembleArchJump(RpoNumber target) {
2016 if (!IsNextInAssemblyOrder(target)) __ b(GetLabel(target)); 1952 if (!IsNextInAssemblyOrder(target)) __ b(GetLabel(target));
2017 } 1953 }
2018 1954
2019 // Assembles boolean materializations after an instruction. 1955 // Assembles boolean materializations after an instruction.
2020 void CodeGenerator::AssembleArchBoolean(Instruction* instr, 1956 void CodeGenerator::AssembleArchBoolean(Instruction* instr,
2021 FlagsCondition condition) { 1957 FlagsCondition condition) {
2022 S390OperandConverter i(this, instr); 1958 S390OperandConverter i(this, instr);
2023 Label done;
2024 ArchOpcode op = instr->arch_opcode(); 1959 ArchOpcode op = instr->arch_opcode();
2025 bool check_unordered = (op == kS390_CmpDouble || kS390_CmpFloat); 1960 bool check_unordered = (op == kS390_CmpDouble || op == kS390_CmpFloat);
2026 1961
2027 // Overflow checked for add/sub only. 1962 // Overflow checked for add/sub only.
2028 DCHECK((condition != kOverflow && condition != kNotOverflow) || 1963 DCHECK((condition != kOverflow && condition != kNotOverflow) ||
2029 (op == kS390_AddWithOverflow32 || op == kS390_SubWithOverflow32) || 1964 (op == kS390_Add32 || kS390_Add64 || op == kS390_Sub32 ||
2030 (op == kS390_Add || op == kS390_Sub)); 1965 op == kS390_Sub64));
2031 1966
2032 // Materialize a full 32-bit 1 or 0 value. The result register is always the 1967 // Materialize a full 32-bit 1 or 0 value. The result register is always the
2033 // last output of the instruction. 1968 // last output of the instruction.
2034 DCHECK_NE(0u, instr->OutputCount()); 1969 DCHECK_NE(0u, instr->OutputCount());
2035 Register reg = i.OutputRegister(instr->OutputCount() - 1); 1970 Register reg = i.OutputRegister(instr->OutputCount() - 1);
2036 Condition cond = FlagsConditionToCondition(condition, op); 1971 Condition cond = FlagsConditionToCondition(condition, op);
2037 switch (cond) { 1972 Label done;
2038 case ne: 1973 if (check_unordered) {
2039 case ge: 1974 __ LoadImmP(reg, (cond == eq || cond == le || cond == lt) ? Operand::Zero()
2040 case gt: 1975 : Operand(1));
2041 if (check_unordered) { 1976 __ bunordered(&done);
2042 __ LoadImmP(reg, Operand(1));
2043 __ LoadImmP(kScratchReg, Operand::Zero());
2044 __ bunordered(&done);
2045 Label cond_true;
2046 __ b(cond, &cond_true, Label::kNear);
2047 __ LoadRR(reg, kScratchReg);
2048 __ bind(&cond_true);
2049 } else {
2050 Label cond_true, done_here;
2051 __ LoadImmP(reg, Operand(1));
2052 __ b(cond, &cond_true, Label::kNear);
2053 __ LoadImmP(reg, Operand::Zero());
2054 __ bind(&cond_true);
2055 }
2056 break;
2057 case eq:
2058 case lt:
2059 case le:
2060 if (check_unordered) {
2061 __ LoadImmP(reg, Operand::Zero());
2062 __ LoadImmP(kScratchReg, Operand(1));
2063 __ bunordered(&done);
2064 Label cond_false;
2065 __ b(NegateCondition(cond), &cond_false, Label::kNear);
2066 __ LoadRR(reg, kScratchReg);
2067 __ bind(&cond_false);
2068 } else {
2069 __ LoadImmP(reg, Operand::Zero());
2070 Label cond_false;
2071 __ b(NegateCondition(cond), &cond_false, Label::kNear);
2072 __ LoadImmP(reg, Operand(1));
2073 __ bind(&cond_false);
2074 }
2075 break;
2076 default:
2077 UNREACHABLE();
2078 break;
2079 } 1977 }
1978 __ LoadImmP(reg, Operand::Zero());
1979 __ LoadImmP(kScratchReg, Operand(1));
1980 // locr is sufficient since reg's upper 32 is guarrantee to be 0
1981 __ locr(cond, reg, kScratchReg);
2080 __ bind(&done); 1982 __ bind(&done);
2081 } 1983 }
2082 1984
2083 void CodeGenerator::AssembleArchLookupSwitch(Instruction* instr) { 1985 void CodeGenerator::AssembleArchLookupSwitch(Instruction* instr) {
2084 S390OperandConverter i(this, instr); 1986 S390OperandConverter i(this, instr);
2085 Register input = i.InputRegister(0); 1987 Register input = i.InputRegister(0);
2086 for (size_t index = 2; index < instr->InputCount(); index += 2) { 1988 for (size_t index = 2; index < instr->InputCount(); index += 2) {
2087 __ Cmp32(input, Operand(i.InputInt32(index + 0))); 1989 __ Cmp32(input, Operand(i.InputInt32(index + 0)));
2088 __ beq(GetLabel(i.InputRpo(index + 1))); 1990 __ beq(GetLabel(i.InputRpo(index + 1)));
2089 } 1991 }
(...skipping 370 matching lines...) Expand 10 before | Expand all | Expand 10 after
2460 padding_size -= 2; 2362 padding_size -= 2;
2461 } 2363 }
2462 } 2364 }
2463 } 2365 }
2464 2366
2465 #undef __ 2367 #undef __
2466 2368
2467 } // namespace compiler 2369 } // namespace compiler
2468 } // namespace internal 2370 } // namespace internal
2469 } // namespace v8 2371 } // namespace v8
OLDNEW
« no previous file with comments | « no previous file | src/compiler/s390/instruction-codes-s390.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698