| OLD | NEW |
| 1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2012, 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/globals.h" | 5 #include "vm/globals.h" |
| 6 #if defined(TARGET_ARCH_X64) | 6 #if defined(TARGET_ARCH_X64) |
| 7 | 7 |
| 8 #include "vm/assembler.h" | 8 #include "vm/assembler.h" |
| 9 #include "vm/os.h" | 9 #include "vm/os.h" |
| 10 #include "vm/unit_test.h" | 10 #include "vm/unit_test.h" |
| (...skipping 1370 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1381 __ ret(); | 1381 __ ret(); |
| 1382 } | 1382 } |
| 1383 | 1383 |
| 1384 | 1384 |
| 1385 ASSEMBLER_TEST_RUN(SingleFPOperations, entry) { | 1385 ASSEMBLER_TEST_RUN(SingleFPOperations, entry) { |
| 1386 typedef float (*SingleFPOperationsCode)(); | 1386 typedef float (*SingleFPOperationsCode)(); |
| 1387 float res = reinterpret_cast<SingleFPOperationsCode>(entry)(); | 1387 float res = reinterpret_cast<SingleFPOperationsCode>(entry)(); |
| 1388 EXPECT_FLOAT_EQ(0.0f, res, 0.001f); | 1388 EXPECT_FLOAT_EQ(0.0f, res, 0.001f); |
| 1389 } | 1389 } |
| 1390 | 1390 |
| 1391 ASSEMBLER_TEST_GENERATE(PackedFPOperations, assembler) { | |
| 1392 __ movq(RAX, Immediate(bit_cast<int32_t, float>(12.3f))); | |
| 1393 __ movd(XMM10, RAX); | |
| 1394 __ shufps(XMM10, XMM10, Immediate(0x0)); | |
| 1395 __ movq(RAX, Immediate(bit_cast<int32_t, float>(3.4f))); | |
| 1396 __ movd(XMM9, RAX); | |
| 1397 __ shufps(XMM9, XMM9, Immediate(0x0)); | |
| 1398 __ addps(XMM10, XMM9); // 15.7f | |
| 1399 __ mulps(XMM10, XMM9); // 53.38f | |
| 1400 __ subps(XMM10, XMM9); // 49.98f | |
| 1401 __ divps(XMM10, XMM9); // 14.7f | |
| 1402 __ movaps(XMM0, XMM10); | |
| 1403 __ shufps(XMM0, XMM0, Immediate(0x55)); // Copy second lane into all 4 lanes. | |
| 1404 __ ret(); | |
| 1405 } | |
| 1406 | |
| 1407 | |
| 1408 ASSEMBLER_TEST_RUN(PackedFPOperations, entry) { | |
| 1409 typedef float (*PackedFPOperationsCode)(); | |
| 1410 float res = reinterpret_cast<PackedFPOperationsCode>(entry)(); | |
| 1411 EXPECT_FLOAT_EQ(14.7f, res, 0.001f); | |
| 1412 } | |
| 1413 | |
| 1414 | |
| 1415 ASSEMBLER_TEST_GENERATE(PackedFPOperations2, assembler) { | |
| 1416 __ movq(RAX, Immediate(bit_cast<int32_t, float>(4.0f))); | |
| 1417 __ movd(XMM0, RAX); | |
| 1418 __ shufps(XMM0, XMM0, Immediate(0x0)); | |
| 1419 | |
| 1420 __ movaps(XMM11, XMM0); // Copy XMM0 | |
| 1421 __ reciprocalps(XMM11); // 0.25 | |
| 1422 __ sqrtps(XMM11); // 0.5 | |
| 1423 __ rsqrtps(XMM0); // ~0.5 | |
| 1424 __ subps(XMM0, XMM11); // ~0.0 | |
| 1425 __ shufps(XMM0, XMM0, Immediate(0x00)); // Copy second lane into all 4 lanes. | |
| 1426 __ ret(); | |
| 1427 } | |
| 1428 | |
| 1429 | |
| 1430 ASSEMBLER_TEST_RUN(PackedFPOperations2, entry) { | |
| 1431 typedef float (*PackedFPOperations2Code)(); | |
| 1432 float res = reinterpret_cast<PackedFPOperations2Code>(entry)(); | |
| 1433 EXPECT_FLOAT_EQ(0.0f, res, 0.001f); | |
| 1434 } | |
| 1435 | |
| 1436 | 1391 |
| 1437 ASSEMBLER_TEST_GENERATE(PackedCompareEQ, assembler) { | |
| 1438 __ set1ps(XMM0, RAX, Immediate(bit_cast<int32_t, float>(2.0f))); | |
| 1439 __ set1ps(XMM1, RAX, Immediate(bit_cast<int32_t, float>(4.0f))); | |
| 1440 __ cmppseq(XMM0, XMM1); | |
| 1441 __ pushq(RAX); | |
| 1442 __ movss(Address(RSP, 0), XMM0); | |
| 1443 __ popq(RAX); | |
| 1444 __ ret(); | |
| 1445 } | |
| 1446 | |
| 1447 | |
| 1448 ASSEMBLER_TEST_RUN(PackedCompareEQ, entry) { | |
| 1449 typedef uint32_t (*PackedCompareEQCode)(); | |
| 1450 uint32_t res = reinterpret_cast<PackedCompareEQCode>(entry)(); | |
| 1451 EXPECT_EQ(static_cast<uword>(0x0), res); | |
| 1452 } | |
| 1453 | |
| 1454 | |
| 1455 ASSEMBLER_TEST_GENERATE(PackedCompareNEQ, assembler) { | |
| 1456 __ set1ps(XMM0, RAX, Immediate(bit_cast<int32_t, float>(2.0f))); | |
| 1457 __ set1ps(XMM1, RAX, Immediate(bit_cast<int32_t, float>(4.0f))); | |
| 1458 __ cmppsneq(XMM0, XMM1); | |
| 1459 __ pushq(RAX); | |
| 1460 __ movss(Address(RSP, 0), XMM0); | |
| 1461 __ popq(RAX); | |
| 1462 __ ret(); | |
| 1463 } | |
| 1464 | |
| 1465 | |
| 1466 ASSEMBLER_TEST_RUN(PackedCompareNEQ, entry) { | |
| 1467 typedef uint32_t (*PackedCompareNEQCode)(); | |
| 1468 uint32_t res = reinterpret_cast<PackedCompareNEQCode>(entry)(); | |
| 1469 EXPECT_EQ(static_cast<uword>(0xFFFFFFFF), res); | |
| 1470 } | |
| 1471 | |
| 1472 | |
| 1473 ASSEMBLER_TEST_GENERATE(PackedCompareLT, assembler) { | |
| 1474 __ set1ps(XMM0, RAX, Immediate(bit_cast<int32_t, float>(2.0f))); | |
| 1475 __ set1ps(XMM1, RAX, Immediate(bit_cast<int32_t, float>(4.0f))); | |
| 1476 __ cmppslt(XMM0, XMM1); | |
| 1477 __ pushq(RAX); | |
| 1478 __ movss(Address(RSP, 0), XMM0); | |
| 1479 __ popq(RAX); | |
| 1480 __ ret(); | |
| 1481 } | |
| 1482 | |
| 1483 | |
| 1484 ASSEMBLER_TEST_RUN(PackedCompareLT, entry) { | |
| 1485 typedef uint32_t (*PackedCompareLTCode)(); | |
| 1486 uint32_t res = reinterpret_cast<PackedCompareLTCode>(entry)(); | |
| 1487 EXPECT_EQ(static_cast<uword>(0xFFFFFFFF), res); | |
| 1488 } | |
| 1489 | |
| 1490 | |
| 1491 ASSEMBLER_TEST_GENERATE(PackedCompareLE, assembler) { | |
| 1492 __ set1ps(XMM0, RAX, Immediate(bit_cast<int32_t, float>(2.0f))); | |
| 1493 __ set1ps(XMM1, RAX, Immediate(bit_cast<int32_t, float>(4.0f))); | |
| 1494 __ cmppsle(XMM0, XMM1); | |
| 1495 __ pushq(RAX); | |
| 1496 __ movss(Address(RSP, 0), XMM0); | |
| 1497 __ popq(RAX); | |
| 1498 __ ret(); | |
| 1499 } | |
| 1500 | |
| 1501 | |
| 1502 ASSEMBLER_TEST_RUN(PackedCompareLE, entry) { | |
| 1503 typedef uint32_t (*PackedCompareLECode)(); | |
| 1504 uint32_t res = reinterpret_cast<PackedCompareLECode>(entry)(); | |
| 1505 EXPECT_EQ(static_cast<uword>(0xFFFFFFFF), res); | |
| 1506 } | |
| 1507 | |
| 1508 | |
| 1509 ASSEMBLER_TEST_GENERATE(PackedCompareNLT, assembler) { | |
| 1510 __ set1ps(XMM0, RAX, Immediate(bit_cast<int32_t, float>(2.0f))); | |
| 1511 __ set1ps(XMM1, RAX, Immediate(bit_cast<int32_t, float>(4.0f))); | |
| 1512 __ cmppsnlt(XMM0, XMM1); | |
| 1513 __ pushq(RAX); | |
| 1514 __ movss(Address(RSP, 0), XMM0); | |
| 1515 __ popq(RAX); | |
| 1516 __ ret(); | |
| 1517 } | |
| 1518 | |
| 1519 | |
| 1520 ASSEMBLER_TEST_RUN(PackedCompareNLT, entry) { | |
| 1521 typedef uint32_t (*PackedCompareNLTCode)(); | |
| 1522 uint32_t res = reinterpret_cast<PackedCompareNLTCode>(entry)(); | |
| 1523 EXPECT_EQ(static_cast<uword>(0x0), res); | |
| 1524 } | |
| 1525 | |
| 1526 | |
| 1527 ASSEMBLER_TEST_GENERATE(PackedCompareNLE, assembler) { | |
| 1528 __ set1ps(XMM0, RAX, Immediate(bit_cast<int32_t, float>(2.0f))); | |
| 1529 __ set1ps(XMM1, RAX, Immediate(bit_cast<int32_t, float>(4.0f))); | |
| 1530 __ cmppsnle(XMM0, XMM1); | |
| 1531 __ pushq(RAX); | |
| 1532 __ movss(Address(RSP, 0), XMM0); | |
| 1533 __ popq(RAX); | |
| 1534 __ ret(); | |
| 1535 } | |
| 1536 | |
| 1537 | |
| 1538 ASSEMBLER_TEST_RUN(PackedCompareNLE, entry) { | |
| 1539 typedef uint32_t (*PackedCompareNLECode)(); | |
| 1540 uint32_t res = reinterpret_cast<PackedCompareNLECode>(entry)(); | |
| 1541 EXPECT_EQ(static_cast<uword>(0x0), res); | |
| 1542 } | |
| 1543 | |
| 1544 | |
| 1545 ASSEMBLER_TEST_GENERATE(PackedNegate, assembler) { | |
| 1546 __ movl(RAX, Immediate(bit_cast<int32_t, float>(12.3f))); | |
| 1547 __ movd(XMM0, RAX); | |
| 1548 __ shufps(XMM0, XMM0, Immediate(0x0)); | |
| 1549 __ negateps(XMM0); | |
| 1550 __ shufps(XMM0, XMM0, Immediate(0xAA)); // Copy third lane into all 4 lanes. | |
| 1551 __ ret(); | |
| 1552 } | |
| 1553 | |
| 1554 | |
| 1555 ASSEMBLER_TEST_RUN(PackedNegate, entry) { | |
| 1556 typedef float (*PackedNegateCode)(); | |
| 1557 float res = reinterpret_cast<PackedNegateCode>(entry)(); | |
| 1558 EXPECT_FLOAT_EQ(-12.3f, res, 0.001f); | |
| 1559 } | |
| 1560 | |
| 1561 | |
| 1562 ASSEMBLER_TEST_GENERATE(PackedAbsolute, assembler) { | |
| 1563 __ movl(RAX, Immediate(bit_cast<int32_t, float>(-15.3f))); | |
| 1564 __ movd(XMM0, RAX); | |
| 1565 __ shufps(XMM0, XMM0, Immediate(0x0)); | |
| 1566 __ absps(XMM0); | |
| 1567 __ shufps(XMM0, XMM0, Immediate(0xAA)); // Copy third lane into all 4 lanes. | |
| 1568 __ ret(); | |
| 1569 } | |
| 1570 | |
| 1571 | |
| 1572 ASSEMBLER_TEST_RUN(PackedAbsolute, entry) { | |
| 1573 typedef float (*PackedAbsoluteCode)(); | |
| 1574 float res = reinterpret_cast<PackedAbsoluteCode>(entry)(); | |
| 1575 EXPECT_FLOAT_EQ(15.3f, res, 0.001f); | |
| 1576 } | |
| 1577 | |
| 1578 | |
| 1579 ASSEMBLER_TEST_GENERATE(PackedSetWZero, assembler) { | |
| 1580 __ set1ps(XMM0, RAX, Immediate(bit_cast<int32_t, float>(12.3f))); | |
| 1581 __ zerowps(XMM0); | |
| 1582 __ shufps(XMM0, XMM0, Immediate(0xFF)); // Copy the W lane which is now 0.0. | |
| 1583 __ ret(); | |
| 1584 } | |
| 1585 | |
| 1586 | |
| 1587 ASSEMBLER_TEST_RUN(PackedSetWZero, entry) { | |
| 1588 typedef float (*PackedSetWZeroCode)(); | |
| 1589 float res = reinterpret_cast<PackedSetWZeroCode>(entry)(); | |
| 1590 EXPECT_FLOAT_EQ(0.0f, res, 0.001f); | |
| 1591 } | |
| 1592 | |
| 1593 | |
| 1594 ASSEMBLER_TEST_GENERATE(PackedMin, assembler) { | |
| 1595 __ set1ps(XMM0, RAX, Immediate(bit_cast<int32_t, float>(2.0f))); | |
| 1596 __ set1ps(XMM1, RAX, Immediate(bit_cast<int32_t, float>(4.0f))); | |
| 1597 __ minps(XMM0, XMM1); | |
| 1598 __ ret(); | |
| 1599 } | |
| 1600 | |
| 1601 | |
| 1602 ASSEMBLER_TEST_RUN(PackedMin, entry) { | |
| 1603 typedef float (*PackedMinCode)(); | |
| 1604 float res = reinterpret_cast<PackedMinCode>(entry)(); | |
| 1605 EXPECT_FLOAT_EQ(2.0f, res, 0.001f); | |
| 1606 } | |
| 1607 | |
| 1608 | |
| 1609 ASSEMBLER_TEST_GENERATE(PackedMax, assembler) { | |
| 1610 __ set1ps(XMM0, RAX, Immediate(bit_cast<int32_t, float>(2.0f))); | |
| 1611 __ set1ps(XMM1, RAX, Immediate(bit_cast<int32_t, float>(4.0f))); | |
| 1612 __ maxps(XMM0, XMM1); | |
| 1613 __ ret(); | |
| 1614 } | |
| 1615 | |
| 1616 | |
| 1617 ASSEMBLER_TEST_RUN(PackedMax, entry) { | |
| 1618 typedef float (*PackedMaxCode)(); | |
| 1619 float res = reinterpret_cast<PackedMaxCode>(entry)(); | |
| 1620 EXPECT_FLOAT_EQ(4.0f, res, 0.001f); | |
| 1621 } | |
| 1622 | |
| 1623 | |
| 1624 ASSEMBLER_TEST_GENERATE(PackedLogicalOr, assembler) { | |
| 1625 static const struct ALIGN16 { | |
| 1626 uint32_t a; | |
| 1627 uint32_t b; | |
| 1628 uint32_t c; | |
| 1629 uint32_t d; | |
| 1630 } constant1 = | |
| 1631 { 0xF0F0F0F0, 0xF0F0F0F0, 0xF0F0F0F0, 0xF0F0F0F0 }; | |
| 1632 static const struct ALIGN16 { | |
| 1633 uint32_t a; | |
| 1634 uint32_t b; | |
| 1635 uint32_t c; | |
| 1636 uint32_t d; | |
| 1637 } constant2 = | |
| 1638 { 0x0F0F0F0F, 0x0F0F0F0F, 0x0F0F0F0F, 0x0F0F0F0F }; | |
| 1639 __ movq(RAX, Immediate(reinterpret_cast<intptr_t>(&constant1))); | |
| 1640 __ movups(XMM0, Address(RAX, 0)); | |
| 1641 __ movq(RAX, Immediate(reinterpret_cast<intptr_t>(&constant2))); | |
| 1642 __ movups(XMM1, Address(RAX, 0)); | |
| 1643 __ orps(XMM0, XMM1); | |
| 1644 __ pushq(RAX); | |
| 1645 __ movss(Address(RSP, 0), XMM0); | |
| 1646 __ popq(RAX); | |
| 1647 __ ret(); | |
| 1648 } | |
| 1649 | |
| 1650 | |
| 1651 ASSEMBLER_TEST_RUN(PackedLogicalOr, entry) { | |
| 1652 typedef uint32_t (*PackedLogicalOrCode)(); | |
| 1653 uint32_t res = reinterpret_cast<PackedLogicalOrCode>(entry)(); | |
| 1654 EXPECT_EQ(0xFFFFFFFF, res); | |
| 1655 } | |
| 1656 | |
| 1657 | |
| 1658 ASSEMBLER_TEST_GENERATE(PackedLogicalAnd, assembler) { | |
| 1659 static const struct ALIGN16 { | |
| 1660 uint32_t a; | |
| 1661 uint32_t b; | |
| 1662 uint32_t c; | |
| 1663 uint32_t d; | |
| 1664 } constant1 = | |
| 1665 { 0xF0F0F0F0, 0xF0F0F0F0, 0xF0F0F0F0, 0xF0F0F0F0 }; | |
| 1666 static const struct ALIGN16 { | |
| 1667 uint32_t a; | |
| 1668 uint32_t b; | |
| 1669 uint32_t c; | |
| 1670 uint32_t d; | |
| 1671 } constant2 = | |
| 1672 { 0x0F0FFF0F, 0x0F0F0F0F, 0x0F0F0F0F, 0x0F0F0F0F }; | |
| 1673 __ movq(RAX, Immediate(reinterpret_cast<intptr_t>(&constant1))); | |
| 1674 __ movups(XMM0, Address(RAX, 0)); | |
| 1675 __ movq(RAX, Immediate(reinterpret_cast<intptr_t>(&constant2))); | |
| 1676 __ andps(XMM0, Address(RAX, 0)); | |
| 1677 __ pushq(RAX); | |
| 1678 __ movss(Address(RSP, 0), XMM0); | |
| 1679 __ popq(RAX); | |
| 1680 __ ret(); | |
| 1681 } | |
| 1682 | |
| 1683 | |
| 1684 ASSEMBLER_TEST_RUN(PackedLogicalAnd, entry) { | |
| 1685 typedef uint32_t (*PackedLogicalAndCode)(); | |
| 1686 uint32_t res = reinterpret_cast<PackedLogicalAndCode>(entry)(); | |
| 1687 EXPECT_EQ(static_cast<uword>(0x0000F000), res); | |
| 1688 } | |
| 1689 | |
| 1690 | |
| 1691 ASSEMBLER_TEST_GENERATE(PackedLogicalNot, assembler) { | |
| 1692 static const struct ALIGN16 { | |
| 1693 uint32_t a; | |
| 1694 uint32_t b; | |
| 1695 uint32_t c; | |
| 1696 uint32_t d; | |
| 1697 } constant1 = | |
| 1698 { 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF }; | |
| 1699 __ movq(RAX, Immediate(reinterpret_cast<intptr_t>(&constant1))); | |
| 1700 __ movups(XMM9, Address(RAX, 0)); | |
| 1701 __ notps(XMM9); | |
| 1702 __ movaps(XMM0, XMM9); | |
| 1703 __ pushq(RAX); | |
| 1704 __ movss(Address(RSP, 0), XMM0); | |
| 1705 __ popq(RAX); | |
| 1706 __ ret(); | |
| 1707 } | |
| 1708 | |
| 1709 | |
| 1710 ASSEMBLER_TEST_RUN(PackedLogicalNot, entry) { | |
| 1711 typedef uint32_t (*PackedLogicalNotCode)(); | |
| 1712 uint32_t res = reinterpret_cast<PackedLogicalNotCode>(entry)(); | |
| 1713 EXPECT_EQ(static_cast<uword>(0x0), res); | |
| 1714 } | |
| 1715 | |
| 1716 ASSEMBLER_TEST_GENERATE(DoubleFPMoves, assembler) { | 1392 ASSEMBLER_TEST_GENERATE(DoubleFPMoves, assembler) { |
| 1717 __ movq(RAX, Immediate(bit_cast<int64_t, double>(1024.67))); | 1393 __ movq(RAX, Immediate(bit_cast<int64_t, double>(1024.67))); |
| 1718 __ pushq(R15); // Callee saved. | 1394 __ pushq(R15); // Callee saved. |
| 1719 __ pushq(RAX); | 1395 __ pushq(RAX); |
| 1720 __ movsd(XMM0, Address(RSP, 0)); | 1396 __ movsd(XMM0, Address(RSP, 0)); |
| 1721 __ movsd(XMM1, XMM0); | 1397 __ movsd(XMM1, XMM0); |
| 1722 __ movsd(XMM2, XMM1); | 1398 __ movsd(XMM2, XMM1); |
| 1723 __ movsd(XMM3, XMM2); | 1399 __ movsd(XMM3, XMM2); |
| 1724 __ movsd(XMM4, XMM3); | 1400 __ movsd(XMM4, XMM3); |
| 1725 __ movsd(XMM5, XMM4); | 1401 __ movsd(XMM5, XMM4); |
| (...skipping 539 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2265 EXPECT_EQ(0, res); | 1941 EXPECT_EQ(0, res); |
| 2266 res = reinterpret_cast<ExtractSignBits>(entry)(-1.0); | 1942 res = reinterpret_cast<ExtractSignBits>(entry)(-1.0); |
| 2267 EXPECT_EQ(1, res); | 1943 EXPECT_EQ(1, res); |
| 2268 res = reinterpret_cast<ExtractSignBits>(entry)(-0.0); | 1944 res = reinterpret_cast<ExtractSignBits>(entry)(-0.0); |
| 2269 EXPECT_EQ(1, res); | 1945 EXPECT_EQ(1, res); |
| 2270 } | 1946 } |
| 2271 | 1947 |
| 2272 } // namespace dart | 1948 } // namespace dart |
| 2273 | 1949 |
| 2274 #endif // defined TARGET_ARCH_X64 | 1950 #endif // defined TARGET_ARCH_X64 |
| OLD | NEW |