Emit fatal when unit takes a reference to a local superglobal
[hiphop-php.git] / hphp / runtime / test / reg-algorithms.cpp
blob3730c203267774eeef9e799edc55c49f0881d5e6
1 /*
2 +----------------------------------------------------------------------+
3 | HipHop for PHP |
4 +----------------------------------------------------------------------+
5 | Copyright (c) 2010-present Facebook, Inc. (http://www.facebook.com) |
6 +----------------------------------------------------------------------+
7 | This source file is subject to version 3.01 of the PHP license, |
8 | that is bundled with this package in the file LICENSE, and is |
9 | available through the world-wide-web at the following url: |
10 | http://www.php.net/license/3_01.txt |
11 | If you did not receive a copy of the PHP license and are unable to |
12 | obtain it through the world-wide-web, please send a note to |
13 | license@php.net so we can mail you a copy immediately. |
14 +----------------------------------------------------------------------+
17 #include "hphp/runtime/vm/jit/reg-algorithms.h"
18 #include "hphp/runtime/vm/jit/phys-reg.h"
20 #include "hphp/util/asm-x64.h"
22 #include <gtest/gtest.h>
24 namespace HPHP { namespace jit { namespace x64 {
26 TEST(RegAlgorithms, twoCycle) {
27 PhysReg::Map<PhysReg> moves;
29 using namespace reg;
30 moves[rax] = rdx;
31 moves[rdx] = rax;
33 auto howTo = doRegMoves(moves, r10);
34 EXPECT_EQ(howTo.size(), 1);
35 EXPECT_EQ(howTo[0].m_kind, MoveInfo::Kind::Xchg);
36 EXPECT_TRUE((howTo[0].m_src == rax && howTo[0].m_dst == rdx) ||
37 (howTo[0].m_src == rdx && howTo[0].m_dst == rax));
40 TEST(RegAlgorithms, threeCycle) {
41 PhysReg::Map<PhysReg> moves;
43 using namespace reg;
44 moves[rax] = rdx;
45 moves[rdx] = rcx;
46 moves[rcx] = rax;
48 auto howTo = doRegMoves(moves, r10);
49 EXPECT_EQ(howTo.size(), 2);
50 EXPECT_EQ(howTo[0].m_kind, MoveInfo::Kind::Xchg);
51 EXPECT_TRUE((howTo[0].m_src == rax && howTo[0].m_dst == rdx) ||
52 (howTo[0].m_src == rdx && howTo[0].m_dst == rax));
53 EXPECT_TRUE((howTo[1].m_src == rdx && howTo[1].m_dst == rcx) ||
54 (howTo[1].m_src == rcx && howTo[1].m_dst == rdx));
56 // another test involving a 3-cycle plus one leaf. pass as long as
57 // it doesn't blow up.
58 moves[rax] = rbx;
59 moves[rcx] = rax;
60 moves[rdx] = rcx; // leaf
61 moves[rbx] = rcx;
62 auto howTo2 = doRegMoves(moves, r10);
65 TEST(RegAlgorithms, noCycle) {
66 PhysReg::Map<PhysReg> moves;
68 using namespace reg;
69 moves[rax] = rdx;
70 moves[rdx] = r13;
71 moves[r13] = r10;
73 auto howTo = doRegMoves(moves, r11);
74 EXPECT_EQ(howTo.size(), 3);
75 EXPECT_EQ(howTo[0].m_kind, MoveInfo::Kind::Move);
76 EXPECT_EQ(howTo[0].m_src, rdx);
77 EXPECT_EQ(howTo[0].m_dst, rax);
78 EXPECT_EQ(howTo[1].m_kind, MoveInfo::Kind::Move);
79 EXPECT_EQ(howTo[1].m_src, r13);
80 EXPECT_EQ(howTo[1].m_dst, rdx);
81 EXPECT_EQ(howTo[2].m_kind, MoveInfo::Kind::Move);
82 EXPECT_EQ(howTo[2].m_src, r10);
83 EXPECT_EQ(howTo[2].m_dst, r13);
86 TEST(RegAlgorithms, outdegTwo) {
87 PhysReg::Map<PhysReg> moves;
89 using namespace reg;
90 moves[rax] = rcx;
91 moves[rdx] = rcx;
93 auto howTo = doRegMoves(moves, r11);
94 EXPECT_EQ(howTo.size(), 2);
95 EXPECT_EQ(howTo[0].m_src, rcx);
96 EXPECT_EQ(howTo[1].m_src, rcx);
97 EXPECT_TRUE((howTo[0].m_dst == rax && howTo[1].m_dst == rdx) ||
98 (howTo[0].m_dst == rdx && howTo[1].m_dst == rax));
101 TEST(RegAlgorithms, simdCycle) {
102 PhysReg::Map<PhysReg> moves;
104 using namespace reg;
105 moves[rax] = xmm0;
106 moves[xmm0] = rax;
108 auto howTo = doRegMoves(moves, r11);
109 EXPECT_EQ(howTo.size(), 3);
110 EXPECT_EQ(howTo[0].m_kind, MoveInfo::Kind::Move);
111 EXPECT_EQ(howTo[0].m_src, rax);
112 EXPECT_EQ(howTo[0].m_dst, r11);
113 EXPECT_EQ(howTo[1].m_kind, MoveInfo::Kind::Move);
114 EXPECT_EQ(howTo[1].m_src, xmm0);
115 EXPECT_EQ(howTo[1].m_dst, rax);
116 EXPECT_EQ(howTo[2].m_kind, MoveInfo::Kind::Move);
117 EXPECT_EQ(howTo[2].m_src, r11);
118 EXPECT_EQ(howTo[2].m_dst, xmm0);