test_gdt_x64.cpp
Go to the documentation of this file.
1 //
2 // Bareflank Hypervisor
3 //
4 // Copyright (C) 2015 Assured Information Security, Inc.
5 // Author: Rian Quinn <quinnr@ainfosec.com>
6 // Author: Brendan Kerrigan <kerriganb@ainfosec.com>
7 //
8 // This library is free software; you can redistribute it and/or
9 // modify it under the terms of the GNU Lesser General Public
10 // License as published by the Free Software Foundation; either
11 // version 2.1 of the License, or (at your option) any later version.
12 //
13 // This library is distributed in the hope that it will be useful,
14 // but WITHOUT ANY WARRANTY; without even the implied warranty of
15 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16 // Lesser General Public License for more details.
17 //
18 // You should have received a copy of the GNU Lesser General Public
19 // License along with this library; if not, write to the Free Software
20 // Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
21 
22 #include <gsl/gsl>
23 
24 #include <test.h>
25 #include <intrinsics/gdt_x64.h>
26 
27 std::vector<gdt_x64::segment_descriptor_type> g_gdt =
28 {
29  0x0,
30  0xFFFFFFFFFFFFFFFF,
31  0xFFFF8FFFFFFFFFFF,
32  0x00000000FFFFFFFF
33 };
34 
36 
37 extern "C" void
39 { *gdt_reg = g_gdt_reg; }
40 
41 extern "C" void
43 { g_gdt_reg = *gdt_reg; }
44 
45 void
46 intrinsics_ut::test_gdt_reg_set_get()
47 {
48  x64::gdt::set(g_gdt.data(), 4 << 3);
49 
50  this->expect_true(x64::gdt::get().base == g_gdt.data());
51  this->expect_true(x64::gdt::get().limit == 4 << 3);
52 }
53 
54 void
55 intrinsics_ut::test_gdt_reg_base_set_get()
56 {
57  x64::gdt::base::set(g_gdt.data());
58  this->expect_true(x64::gdt::base::get() == g_gdt.data());
59 }
60 
61 void
62 intrinsics_ut::test_gdt_reg_limit_set_get()
63 {
64  x64::gdt::limit::set(4 << 3);
65  this->expect_true(x64::gdt::limit::get() == 4 << 3);
66 }
67 
68 void
69 intrinsics_ut::test_gdt_constructor_no_size()
70 {
71  gdt_x64 gdt;
72 }
73 
74 void
75 intrinsics_ut::test_gdt_constructor_zero_size()
76 {
77  this->expect_no_exception([&] { gdt_x64{0}; });
78 }
79 
80 void
81 intrinsics_ut::test_gdt_constructor_size()
82 {
83  gdt_x64 gdt{4};
84  this->expect_true(gdt.base() != 0);
85  this->expect_true(gdt.limit() == 4 * sizeof(gdt_x64::segment_descriptor_type));
86 }
87 
88 void
89 intrinsics_ut::test_gdt_base()
90 {
91  gdt_x64 gdt;
92  this->expect_true(gdt.base() == reinterpret_cast<gdt_x64::integer_pointer>(g_gdt.data()));
93 }
94 
95 void
96 intrinsics_ut::test_gdt_limit()
97 {
98  gdt_x64 gdt;
99  this->expect_true(gdt.limit() == 4 * sizeof(gdt_x64::segment_descriptor_type));
100 }
101 
102 void
103 intrinsics_ut::test_gdt_set_base_zero_index()
104 {
105  gdt_x64 gdt;
106  this->expect_exception([&] { gdt.set_base(0, 0x10); }, ""_ut_ffe);
107 }
108 
109 void
110 intrinsics_ut::test_gdt_set_base_invalid_index()
111 {
112  gdt_x64 gdt;
113  this->expect_exception([&] { gdt.set_base(1000, 0x10); }, ""_ut_ore);
114 }
115 
116 void
117 intrinsics_ut::test_gdt_set_base_tss_at_end_of_gdt()
118 {
119  gdt_x64 gdt;
120  this->expect_exception([&] { gdt.set_base(3, 0x10); }, ""_ut_ore);
121 }
122 
123 void
124 intrinsics_ut::test_gdt_set_base_descriptor_success()
125 {
126  gdt_x64 gdt;
127 
128  this->expect_no_exception([&] { gdt.set_base(1, 0xBBBBBBBB12345678); });
129  this->expect_true(gdt.m_gdt.at(1) == 0x12FFFF345678FFFF);
130 }
131 
132 void
133 intrinsics_ut::test_gdt_set_base_tss_success()
134 {
135  gdt_x64 gdt;
136 
137  this->expect_no_exception([&] { gdt.set_base(2, 0x1234567812345678); });
138  this->expect_true(gdt.m_gdt.at(2) == 0x12FF8F345678FFFF);
139  this->expect_true(gdt.m_gdt.at(3) == 0x0000000012345678);
140 }
141 
142 void
143 intrinsics_ut::test_gdt_base_zero_index()
144 {
145  gdt_x64 gdt;
146  this->expect_exception([&] { gdt.base(0); }, ""_ut_ffe);
147 }
148 
149 void
150 intrinsics_ut::test_gdt_base_invalid_index()
151 {
152  gdt_x64 gdt;
153  this->expect_exception([&] { gdt.base(1000); }, ""_ut_ore);
154 }
155 
156 void
157 intrinsics_ut::test_gdt_base_tss_at_end_of_gdt()
158 {
159  gdt_x64 gdt;
160  this->expect_exception([&] { gdt.base(3); }, ""_ut_ore);
161 }
162 
163 void
164 intrinsics_ut::test_gdt_base_descriptor_success()
165 {
166  gdt_x64 gdt;
167 
168  gdt.m_gdt.at(1) = 0x12FFFF345678FFFF;
169  this->expect_true(gdt.base(1) == 0x0000000012345678);
170 }
171 
172 void
173 intrinsics_ut::test_gdt_base_tss_success()
174 {
175  gdt_x64 gdt;
176 
177  gdt.m_gdt.at(2) = 0x12FF8F345678FFFF;
178  gdt.m_gdt.at(3) = 0x0000000012345678;
179  this->expect_true(gdt.base(2) == 0x1234567812345678);
180 }
181 
182 void
183 intrinsics_ut::test_gdt_set_limit_zero_index()
184 {
185  gdt_x64 gdt;
186  this->expect_exception([&] { gdt.set_limit(0, 0x10); }, ""_ut_ffe);
187 }
188 
189 void
190 intrinsics_ut::test_gdt_set_limit_invalid_index()
191 {
192  gdt_x64 gdt;
193  this->expect_exception([&] { gdt.set_limit(1000, 0x10); }, ""_ut_ore);
194 }
195 
196 void
197 intrinsics_ut::test_gdt_set_limit_descriptor_success()
198 {
199  gdt_x64 gdt;
200 
201  this->expect_no_exception([&] { gdt.set_limit(1, 0x12345678); });
202  this->expect_true(gdt.m_gdt.at(1) == 0xFFF1FFFFFFFF2345);
203 }
204 
205 void
206 intrinsics_ut::test_gdt_limit_zero_index()
207 {
208  gdt_x64 gdt;
209  this->expect_exception([&] { gdt.limit(0); }, ""_ut_ffe);
210 }
211 
212 void
213 intrinsics_ut::test_gdt_limit_invalid_index()
214 {
215  gdt_x64 gdt;
216  this->expect_exception([&] { gdt.limit(1000); }, ""_ut_ore);
217 }
218 
219 void
220 intrinsics_ut::test_gdt_limit_descriptor_success()
221 {
222  gdt_x64 gdt;
223 
224  gdt.m_gdt.at(1) = 0xFFF4FFFFFFFF5678;
225  this->expect_true(gdt.limit(1) == 0x0000000045678FFF);
226 }
227 
228 void
229 intrinsics_ut::test_gdt_limit_descriptor_in_bytes_success()
230 {
231  gdt_x64 gdt;
232 
233  gdt.m_gdt.at(1) = 0xFF74FFFFFFFF5678;
234  this->expect_true(gdt.limit(1) == 0x0000000000045678);
235 }
236 
237 void
238 intrinsics_ut::test_gdt_set_access_rights_zero_index()
239 {
240  gdt_x64 gdt;
241  this->expect_exception([&] { gdt.set_access_rights(0, 0x10); }, ""_ut_ffe);
242 }
243 
244 void
245 intrinsics_ut::test_gdt_set_access_rights_invalid_index()
246 {
247  gdt_x64 gdt;
248  this->expect_exception([&] { gdt.set_access_rights(1000, 0x10); }, ""_ut_ore);
249 }
250 
251 void
252 intrinsics_ut::test_gdt_set_access_rights_descriptor_success()
253 {
254  gdt_x64 gdt;
255 
256  this->expect_no_exception([&] { gdt.set_access_rights(1, 0x12345678); });
257  this->expect_true(gdt.m_gdt.at(1) == 0xFF5F78FFFFFFFFFF);
258 }
259 
260 void
261 intrinsics_ut::test_gdt_access_rights_zero_index()
262 {
263  gdt_x64 gdt;
264  this->expect_exception([&] { gdt.access_rights(0); }, ""_ut_ffe);
265 }
266 
267 void
268 intrinsics_ut::test_gdt_access_rights_invalid_index()
269 {
270  gdt_x64 gdt;
271  this->expect_exception([&] { gdt.access_rights(1000); }, ""_ut_ore);
272 }
273 
274 void
275 intrinsics_ut::test_gdt_access_rights_descriptor_success()
276 {
277  gdt_x64 gdt;
278 
279  gdt.m_gdt.at(1) = 0xFF5F78FFFFFFFFFF;
280  this->expect_true(gdt.access_rights(1) == 0x0000000000005078);
281 }
#define expect_exception(f, e)
Definition: unittest.h:162
uint64_t segment_descriptor_type
Definition: gdt_x64.h:200
access_rights_type access_rights(index_type index) const
Definition: gdt_x64.h:534
void __read_gdt(gdt_reg_x64_t *gdt_reg) noexcept
#define expect_no_exception(f)
Definition: unittest.h:198
void set_base(index_type index, base_type base)
Definition: gdt_x64.h:293
void set_access_rights(index_type index, access_rights_type access_rights)
Definition: gdt_x64.h:501
void set(gdt_reg_x64_t::limit_type limit) noexcept
Definition: gdt_x64.h:121
void set(gdt_reg_x64_t::base_type base) noexcept
Definition: gdt_x64.h:101
void set_limit(index_type index, limit_type limit)
Definition: gdt_x64.h:416
void uint64_t uint64_t uint64_t *rdx noexcept
auto get() noexcept
Definition: gdt_x64.h:113
gdt_reg_x64_t g_gdt_reg
void __write_gdt(gdt_reg_x64_t *gdt_reg) noexcept
void set(gdt_reg_x64_t::base_type base, gdt_reg_x64_t::limit_type limit) noexcept
Definition: gdt_x64.h:85
integer_pointer base() const
Definition: gdt_x64.h:260
auto get() noexcept
Definition: gdt_x64.h:93
size_type limit() const
Definition: gdt_x64.h:270
auto get() noexcept
Definition: gdt_x64.h:77
std::vector< gdt_x64::segment_descriptor_type > g_gdt
uintptr_t integer_pointer
Definition: gdt_x64.h:196
#define expect_true(a)