OLD | NEW |
---|---|
1 // Copyright (c) 2016, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2016, 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 <setjmp.h> // NOLINT | 5 #include <setjmp.h> // NOLINT |
6 #include <stdlib.h> | 6 #include <stdlib.h> |
7 | 7 |
8 #include "vm/globals.h" | 8 #include "vm/globals.h" |
9 #if defined(TARGET_ARCH_DBC) | 9 #if defined(TARGET_ARCH_DBC) |
10 | 10 |
(...skipping 88 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
99 | 99 |
100 DART_FORCE_INLINE static RawObject** FrameArguments(RawObject** FP, | 100 DART_FORCE_INLINE static RawObject** FrameArguments(RawObject** FP, |
101 intptr_t argc) { | 101 intptr_t argc) { |
102 return FP - (kDartFrameFixedSize + argc); | 102 return FP - (kDartFrameFixedSize + argc); |
103 } | 103 } |
104 | 104 |
105 | 105 |
106 class SimulatorHelpers { | 106 class SimulatorHelpers { |
107 public: | 107 public: |
108 DART_FORCE_INLINE static RawSmi* GetClassIdAsSmi(RawObject* obj) { | 108 DART_FORCE_INLINE static RawSmi* GetClassIdAsSmi(RawObject* obj) { |
109 return Smi::New(obj->IsHeapObject() ? obj->GetClassId() : kSmiCid); | 109 return Smi::New(obj->IsHeapObject() ? obj->GetClassId() |
110 : static_cast<intptr_t>(kSmiCid)); | |
110 } | 111 } |
111 | 112 |
112 DART_FORCE_INLINE static intptr_t GetClassId(RawObject* obj) { | 113 DART_FORCE_INLINE static intptr_t GetClassId(RawObject* obj) { |
113 return obj->IsHeapObject() ? obj->GetClassId() : kSmiCid; | 114 return obj->IsHeapObject() ? obj->GetClassId() |
115 : static_cast<intptr_t>(kSmiCid); | |
114 } | 116 } |
115 | 117 |
116 DART_FORCE_INLINE static void IncrementUsageCounter(RawICData* icdata) { | 118 DART_FORCE_INLINE static void IncrementUsageCounter(RawICData* icdata) { |
117 reinterpret_cast<RawFunction*>(icdata->ptr()->owner_) | 119 reinterpret_cast<RawFunction*>(icdata->ptr()->owner_) |
118 ->ptr() | 120 ->ptr() |
119 ->usage_counter_++; | 121 ->usage_counter_++; |
120 } | 122 } |
121 | 123 |
122 DART_FORCE_INLINE static bool IsStrictEqualWithNumberCheck(RawObject* lhs, | 124 DART_FORCE_INLINE static bool IsStrictEqualWithNumberCheck(RawObject* lhs, |
123 RawObject* rhs) { | 125 RawObject* rhs) { |
(...skipping 207 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
331 uint32_t* pc) { | 333 uint32_t* pc) { |
332 frame[0] = Function::null(); | 334 frame[0] = Function::null(); |
333 frame[1] = Code::null(); | 335 frame[1] = Code::null(); |
334 frame[2] = reinterpret_cast<RawObject*>(pc); | 336 frame[2] = reinterpret_cast<RawObject*>(pc); |
335 frame[3] = reinterpret_cast<RawObject*>(base); | 337 frame[3] = reinterpret_cast<RawObject*>(base); |
336 fp_ = sp_ = frame + kDartFrameFixedSize; | 338 fp_ = sp_ = frame + kDartFrameFixedSize; |
337 thread->set_top_exit_frame_info(reinterpret_cast<uword>(sp_)); | 339 thread->set_top_exit_frame_info(reinterpret_cast<uword>(sp_)); |
338 } | 340 } |
339 | 341 |
340 | 342 |
341 #if defined(__has_builtin) | 343 DART_FORCE_INLINE static bool SignedAddWithOverflow(intptr_t lhs, |
Vyacheslav Egorov (Google)
2016/04/22 06:22:04
Where did this go?
Inline assembly is just a fall
zra
2016/04/22 19:40:49
I found the problem with the intrinsics. Their use
Vyacheslav Egorov (Google)
2016/04/23 18:58:35
Good catch! Alternative would be to just rewrite S
zra
2016/04/25 15:42:56
Assuming the intrinsic does a branch to decide the
| |
342 #if __has_builtin(__builtin_smul_overflow) | 344 intptr_t rhs, |
343 #define HAS_MUL_OVERFLOW | |
344 #endif | |
345 #if __has_builtin(__builtin_sadd_overflow) | |
346 #define HAS_ADD_OVERFLOW | |
347 #endif | |
348 #if __has_builtin(__builtin_ssub_overflow) | |
349 #define HAS_SUB_OVERFLOW | |
350 #endif | |
351 #endif | |
352 | |
353 | |
354 DART_FORCE_INLINE static bool SignedAddWithOverflow(int32_t lhs, | |
355 int32_t rhs, | |
356 intptr_t* out) { | 345 intptr_t* out) { |
357 int32_t res = 1; | 346 int32_t res = 1; |
Vyacheslav Egorov (Google)
2016/04/22 06:22:04
if you make this intptr_t then both ARM and ARM64
zra
2016/04/22 19:40:49
Done.
| |
358 #if defined(HAS_ADD_OVERFLOW) | 347 #if defined(HOST_ARCH_IA32) || defined(HOST_ARCH_X64) |
359 res = static_cast<int32_t>(__builtin_sadd_overflow( | |
360 lhs, rhs, reinterpret_cast<int32_t*>(out))); | |
361 #elif defined(__i386__) | |
362 asm volatile( | 348 asm volatile( |
363 "add %2, %1\n" | 349 "add %2, %1\n" |
Ivan Posva
2016/04/21 23:35:15
Shouldn't this be at least an addq for HOST_ARCH_X
zra
2016/04/22 19:40:49
The correct ops for the types of the provided oper
| |
364 "jo 1f;\n" | 350 "jo 1f;\n" |
365 "xor %0, %0\n" | 351 "xor %0, %0\n" |
366 "mov %1, 0(%3)\n" | 352 "mov %1, 0(%3)\n" |
367 "1: " | 353 "1: " |
368 : "+r"(res), "+r"(lhs) | 354 : "+r"(res), "+r"(lhs) |
369 : "r"(rhs), "r"(out) | 355 : "r"(rhs), "r"(out) |
370 : "cc"); | 356 : "cc"); |
371 #elif defined(__arm__) | 357 #elif defined(HOST_ARCH_ARM) |
372 asm volatile( | 358 asm volatile( |
373 "adds %1, %1, %2;\n" | 359 "adds %1, %1, %2;\n" |
374 "bvs 1f;\n" | 360 "bvs 1f;\n" |
375 "mov %0, $0;\n" | 361 "mov %0, $0;\n" |
376 "str %1, [%3, #0]\n" | 362 "str %1, [%3, #0]\n" |
377 "1:" | 363 "1:" |
378 : "+r"(res), "+r"(lhs) | 364 : "+r"(res), "+r"(lhs) |
379 : "r"(rhs), "r"(out) | 365 : "r"(rhs), "r"(out) |
380 : "cc", "r12"); | 366 : "cc", "r12"); |
367 #elif defined(HOST_ARCH_ARM64) | |
368 asm volatile( | |
369 "adds %1, %1, %2;\n" | |
370 "bvs 1f;\n" | |
371 "mov %w0, #0;\n" | |
372 "str %1, [%3, #0]\n" | |
373 "1:" | |
374 : "+r"(res), "+r"(lhs) | |
375 : "r"(rhs), "r"(out) | |
376 : "cc"); | |
381 #else | 377 #else |
382 #error "Unsupported platform" | 378 #error "Unsupported platform" |
383 #endif | 379 #endif |
384 return (res != 0); | 380 return (res != 0); |
385 } | 381 } |
386 | 382 |
387 | 383 |
388 DART_FORCE_INLINE static bool SignedSubWithOverflow(int32_t lhs, | 384 DART_FORCE_INLINE static bool SignedSubWithOverflow(intptr_t lhs, |
389 int32_t rhs, | 385 intptr_t rhs, |
390 intptr_t* out) { | 386 intptr_t* out) { |
391 int32_t res = 1; | 387 int32_t res = 1; |
392 #if defined(HAS_SUB_OVERFLOW) | 388 #if defined(HOST_ARCH_IA32) || defined(HOST_ARCH_X64) |
Ivan Posva
2016/04/21 23:35:15
dittoq
zra
2016/04/22 19:40:49
Acknowledged.
| |
393 res = static_cast<int32_t>(__builtin_ssub_overflow( | |
394 lhs, rhs, reinterpret_cast<int32_t*>(out))); | |
395 #elif defined(__i386__) | |
396 asm volatile( | 389 asm volatile( |
397 "sub %2, %1\n" | 390 "sub %2, %1\n" |
398 "jo 1f;\n" | 391 "jo 1f;\n" |
399 "xor %0, %0\n" | 392 "xor %0, %0\n" |
400 "mov %1, 0(%3)\n" | 393 "mov %1, 0(%3)\n" |
401 "1: " | 394 "1: " |
402 : "+r"(res), "+r"(lhs) | 395 : "+r"(res), "+r"(lhs) |
403 : "r"(rhs), "r"(out) | 396 : "r"(rhs), "r"(out) |
404 : "cc"); | 397 : "cc"); |
405 #elif defined(__arm__) | 398 #elif defined(HOST_ARCH_ARM) |
406 asm volatile( | 399 asm volatile( |
407 "subs %1, %1, %2;\n" | 400 "subs %1, %1, %2;\n" |
408 "bvs 1f;\n" | 401 "bvs 1f;\n" |
409 "mov %0, $0;\n" | 402 "mov %0, $0;\n" |
410 "str %1, [%3, #0]\n" | 403 "str %1, [%3, #0]\n" |
411 "1:" | 404 "1:" |
412 : "+r"(res), "+r"(lhs) | 405 : "+r"(res), "+r"(lhs) |
413 : "r"(rhs), "r"(out) | 406 : "r"(rhs), "r"(out) |
414 : "cc", "r12"); | 407 : "cc", "r12"); |
408 #elif defined(HOST_ARCH_ARM64) | |
409 asm volatile( | |
410 "subs %1, %1, %2;\n" | |
411 "bvs 1f;\n" | |
412 "mov %w0, #0;\n" | |
413 "str %1, [%3, #0]\n" | |
414 "1:" | |
415 : "+r"(res), "+r"(lhs) | |
416 : "r"(rhs), "r"(out) | |
417 : "cc"); | |
415 #else | 418 #else |
416 #error "Unsupported platform" | 419 #error "Unsupported platform" |
417 #endif | 420 #endif |
418 return (res != 0); | 421 return (res != 0); |
419 } | 422 } |
420 | 423 |
421 | 424 |
422 DART_FORCE_INLINE static bool SignedMulWithOverflow(int32_t lhs, | 425 DART_FORCE_INLINE static bool SignedMulWithOverflow(intptr_t lhs, |
423 int32_t rhs, | 426 intptr_t rhs, |
424 intptr_t* out) { | 427 intptr_t* out) { |
425 int32_t res = 1; | 428 int32_t res = 1; |
426 #if defined(HAS_MUL_OVERFLOW) | 429 #if defined(HOST_ARCH_IA32) || defined(HOST_ARCH_X64) |
Ivan Posva
2016/04/21 23:35:15
dittoq
zra
2016/04/22 19:40:49
Acknowledged.
| |
427 res = static_cast<int32_t>(__builtin_smul_overflow( | |
428 lhs, rhs, reinterpret_cast<int32_t*>(out))); | |
429 #elif defined(__i386__) | |
430 asm volatile( | 430 asm volatile( |
431 "imul %2, %1\n" | 431 "imul %2, %1\n" |
432 "jo 1f;\n" | 432 "jo 1f;\n" |
433 "xor %0, %0\n" | 433 "xor %0, %0\n" |
434 "mov %1, 0(%3)\n" | 434 "mov %1, 0(%3)\n" |
435 "1: " | 435 "1: " |
436 : "+r"(res), "+r"(lhs) | 436 : "+r"(res), "+r"(lhs) |
437 : "r"(rhs), "r"(out) | 437 : "r"(rhs), "r"(out) |
438 : "cc"); | 438 : "cc"); |
439 #elif defined(__arm__) | 439 #elif defined(HOST_ARCH_ARM) |
440 asm volatile( | 440 asm volatile( |
441 "smull %1, ip, %1, %2;\n" | 441 "smull %1, ip, %1, %2;\n" |
442 "cmp ip, %1, ASR #31;\n" | 442 "cmp ip, %1, ASR #31;\n" |
443 "bne 1f;\n" | 443 "bne 1f;\n" |
444 "mov %0, $0;\n" | 444 "mov %0, $0;\n" |
445 "str %1, [%3, #0]\n" | 445 "str %1, [%3, #0]\n" |
446 "1:" | 446 "1:" |
447 : "+r"(res), "+r"(lhs) | 447 : "+r"(res), "+r"(lhs) |
448 : "r"(rhs), "r"(out) | 448 : "r"(rhs), "r"(out) |
449 : "cc", "r12"); | 449 : "cc", "r12"); |
450 #elif defined(HOST_ARCH_ARM64) | |
451 int64_t prod_lo; | |
452 asm volatile( | |
453 "mul %1, %2, %3\n" | |
454 "smulh %2, %2, %3\n" | |
455 "cmp %2, %1, ASR #63;\n" | |
456 "bne 1f;\n" | |
457 "mov %w0, #0;\n" | |
458 "str %1, [%4, #0]\n" | |
459 "1:" | |
460 : "+r"(res), "+r"(prod_lo), "+r"(lhs) | |
461 : "r"(rhs), "r"(out) | |
462 : "cc"); | |
450 #else | 463 #else |
451 #error "Unsupported platform" | 464 #error "Unsupported platform" |
452 #endif | 465 #endif |
453 return (res != 0); | 466 return (res != 0); |
454 } | 467 } |
455 | 468 |
456 | 469 |
457 #define LIKELY(cond) __builtin_expect((cond), 1) | 470 #define LIKELY(cond) __builtin_expect((cond), 1) |
458 | 471 |
459 | 472 |
(...skipping 1437 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1897 special_[kExceptionSpecialIndex] = raw_exception; | 1910 special_[kExceptionSpecialIndex] = raw_exception; |
1898 special_[kStacktraceSpecialIndex] = raw_stacktrace; | 1911 special_[kStacktraceSpecialIndex] = raw_stacktrace; |
1899 buf->Longjmp(); | 1912 buf->Longjmp(); |
1900 UNREACHABLE(); | 1913 UNREACHABLE(); |
1901 } | 1914 } |
1902 | 1915 |
1903 } // namespace dart | 1916 } // namespace dart |
1904 | 1917 |
1905 | 1918 |
1906 #endif // defined TARGET_ARCH_DBC | 1919 #endif // defined TARGET_ARCH_DBC |
OLD | NEW |