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

Side by Side Diff: runtime/lib/integers.cc

Issue 8984003: Port code generator to x64. (Closed) Base URL: http://dart.googlecode.com/svn/branches/bleeding_edge/dart/
Patch Set: Created 9 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 | Annotate | Revision Log
« no previous file with comments | « no previous file | runtime/vm/assembler_macros_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) 2011, the Dart project authors. Please see the AUTHORS file 1 // Copyright (c) 2011, 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/bootstrap_natives.h" 5 #include "vm/bootstrap_natives.h"
6 6
7 #include "vm/bigint_operations.h" 7 #include "vm/bigint_operations.h"
8 #include "vm/dart_entry.h" 8 #include "vm/dart_entry.h"
9 #include "vm/exceptions.h" 9 #include "vm/exceptions.h"
10 #include "vm/native_entry.h" 10 #include "vm/native_entry.h"
(...skipping 185 matching lines...) Expand 10 before | Expand all | Expand 10 after
196 OS::Print("Integer_bitXorFromInteger %s ^ %s\n", 196 OS::Print("Integer_bitXorFromInteger %s ^ %s\n",
197 left.ToCString(), right.ToCString()); 197 left.ToCString(), right.ToCString());
198 } 198 }
199 Integer& result = Integer::Handle( 199 Integer& result = Integer::Handle(
200 IntegerBitOperation(Token::kBIT_XOR, left, right)); 200 IntegerBitOperation(Token::kBIT_XOR, left, right));
201 arguments->SetReturn(Integer::Handle(AsInteger(result))); 201 arguments->SetReturn(Integer::Handle(AsInteger(result)));
202 } 202 }
203 203
204 204
205 // The result is invalid if it is outside the range 205 // The result is invalid if it is outside the range
206 // Smi::kMaxValue..Smi::kMinValue. 206 // Smi::kMinValue..Smi::kMaxValue.
207 static int64_t BinaryOpWithTwoSmis(Token::Kind operation, 207 static int64_t BinaryOpWithTwoSmis(Token::Kind operation,
208 const Smi& left, 208 const Smi& left,
209 const Smi& right) { 209 const Smi& right) {
210 switch (operation) { 210 switch (operation) {
211 case Token::kADD: 211 case Token::kADD:
212 return left.Value() + right.Value(); 212 return left.Value() + right.Value();
cshapiro 2011/12/17 00:09:44 This needs an overflow check for 64-bit.
regis 2011/12/17 00:47:44 I think we are fine here, because both operands ar
213 case Token::kSUB: 213 case Token::kSUB:
214 return left.Value() - right.Value(); 214 return left.Value() - right.Value();
215 case Token::kMUL: { 215 case Token::kMUL: {
216 #if defined(TARGET_ARCH_X64) 216 const Bigint& big_left =
cshapiro 2011/12/17 00:09:44 This needs a TODO since it may cause a performance
regis 2011/12/17 00:47:44 Done.
217 // Overflow check for 64-bit platforms unimplemented. 217 Bigint::Handle(BigintOperations::NewFromSmi(left));
218 UNIMPLEMENTED(); 218 const Bigint& big_right =
219 return 0; 219 Bigint::Handle(BigintOperations::NewFromSmi(right));
220 #else 220 const Bigint& big_result =
221 int64_t result_64 = 221 Bigint::Handle(BigintOperations::Multiply(big_left, big_right));
222 static_cast<int64_t>(left.Value()) * 222 if (BigintOperations::FitsIntoInt64(big_result)) {
223 static_cast<int64_t>(right.Value()); 223 return BigintOperations::ToInt64(big_result);
224 return result_64; 224 } else {
225 #endif 225 // Overflow, return an invalid Smi.
226 return Smi::kMaxValue + 1;
227 }
226 } 228 }
227 case Token::kTRUNCDIV: 229 case Token::kTRUNCDIV:
228 return left.Value() / right.Value(); 230 return left.Value() / right.Value();
229 case Token::kMOD: { 231 case Token::kMOD: {
230 intptr_t remainder = left.Value() % right.Value(); 232 intptr_t remainder = left.Value() % right.Value();
231 if (remainder < 0) { 233 if (remainder < 0) {
232 if (right.Value() < 0) { 234 if (right.Value() < 0) {
233 return remainder - right.Value(); 235 return remainder - right.Value();
234 } else { 236 } else {
235 return remainder + right.Value(); 237 return remainder + right.Value();
(...skipping 42 matching lines...) Expand 10 before | Expand all | Expand 10 after
278 const Integer& right_int) { 280 const Integer& right_int) {
279 if (left_int.IsSmi() && right_int.IsSmi()) { 281 if (left_int.IsSmi() && right_int.IsSmi()) {
280 Smi& left_smi = Smi::Handle(); 282 Smi& left_smi = Smi::Handle();
281 Smi& right_smi = Smi::Handle(); 283 Smi& right_smi = Smi::Handle();
282 left_smi ^= left_int.raw(); 284 left_smi ^= left_int.raw();
283 right_smi ^= right_int.raw(); 285 right_smi ^= right_int.raw();
284 int64_t result = BinaryOpWithTwoSmis(operation, left_smi, right_smi); 286 int64_t result = BinaryOpWithTwoSmis(operation, left_smi, right_smi);
285 if (Smi::IsValid64(result)) { 287 if (Smi::IsValid64(result)) {
286 return Smi::New(result); 288 return Smi::New(result);
287 } else { 289 } else {
290 // TODO(regis): This is not going to work on x64. Check other operations.
291 #if defined(TARGET_ARCH_X64)
292 UNIMPLEMENTED();
293 return 0;
294 #else
288 // Overflow to Mint. 295 // Overflow to Mint.
289 return Mint::New(result); 296 return Mint::New(result);
297 #endif
290 } 298 }
291 } else if (AreBoth64bitOperands(left_int, right_int)) { 299 } else if (AreBoth64bitOperands(left_int, right_int)) {
292 // TODO(srdjan): Test for overflow of result instead of operand 300 // TODO(srdjan): Test for overflow of result instead of operand
293 // types. 301 // types.
294 const int64_t a = left_int.AsInt64Value(); 302 const int64_t a = left_int.AsInt64Value();
295 const int64_t b = right_int.AsInt64Value(); 303 const int64_t b = right_int.AsInt64Value();
296 switch (operation) { 304 switch (operation) {
297 case Token::kADD: 305 case Token::kADD:
298 return Integer::New(a + b); 306 return Integer::New(a + b);
299 case Token::kSUB: 307 case Token::kSUB:
(...skipping 279 matching lines...) Expand 10 before | Expand all | Expand 10 after
579 587
580 DEFINE_NATIVE_ENTRY(Bigint_bitNegate, 1) { 588 DEFINE_NATIVE_ENTRY(Bigint_bitNegate, 1) {
581 const Bigint& value = Bigint::CheckedHandle(arguments->At(0)); 589 const Bigint& value = Bigint::CheckedHandle(arguments->At(0));
582 const Bigint& result = Bigint::Handle(BigintOperations::BitNot(value)); 590 const Bigint& result = Bigint::Handle(BigintOperations::BitNot(value));
583 ASSERT(CheckInteger(value)); 591 ASSERT(CheckInteger(value));
584 ASSERT(CheckInteger(result)); 592 ASSERT(CheckInteger(result));
585 arguments->SetReturn(Integer::Handle(AsInteger(result))); 593 arguments->SetReturn(Integer::Handle(AsInteger(result)));
586 } 594 }
587 595
588 } // namespace dart 596 } // namespace dart
OLDNEW
« no previous file with comments | « no previous file | runtime/vm/assembler_macros_x64.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698