1 //===-- ScalarTest.cpp ----------------------------------------------------===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
8 
9 #include "gtest/gtest.h"
10 
11 #include "lldb/Utility/DataExtractor.h"
12 #include "lldb/Utility/Endian.h"
13 #include "lldb/Utility/Scalar.h"
14 #include "lldb/Utility/Status.h"
15 #include "lldb/Utility/StreamString.h"
16 #include "llvm/Testing/Support/Error.h"
17 
18 using namespace lldb_private;
19 using llvm::APFloat;
20 using llvm::APInt;
21 using llvm::Failed;
22 using llvm::Succeeded;
23 
24 template <typename T>
checkInequality(T c1,T c2)25 bool checkInequality(T c1, T c2) {
26   return (Scalar(c1) != Scalar(c2));
27 }
28 
29 template <typename T>
checkEquality(T c1,T c2)30 bool checkEquality(T c1, T c2) {
31   return (Scalar(c1) == Scalar(c2));
32 }
33 
TEST(ScalarTest,Equality)34 TEST(ScalarTest, Equality) {
35   ASSERT_TRUE(checkInequality<int>(23, 24));
36   ASSERT_TRUE(checkEquality<int>(96, 96));
37   ASSERT_TRUE(checkInequality<float>(4.0f, 4.5f));
38   ASSERT_TRUE(checkEquality<float>(4.0f, 4.0f));
39 
40   auto apint1 = APInt(64, 234);
41   auto apint2 = APInt(64, 246);
42   ASSERT_TRUE(checkInequality<APInt>(apint1, apint2));
43   ASSERT_TRUE(checkEquality<APInt>(apint1, apint1));
44 
45   Scalar void1;
46   Scalar void2;
47   float f1 = 2.0;
48   ASSERT_TRUE(void1 == void2);
49   ASSERT_FALSE(void1 == Scalar(f1));
50 }
51 
TEST(ScalarTest,Comparison)52 TEST(ScalarTest, Comparison) {
53   auto s1 = Scalar(23);
54   auto s2 = Scalar(46);
55   ASSERT_TRUE(s1 < s2);
56   ASSERT_TRUE(s1 <= s2);
57   ASSERT_TRUE(s2 > s1);
58   ASSERT_TRUE(s2 >= s1);
59 }
60 
TEST(ScalarTest,ComparisonFloat)61 TEST(ScalarTest, ComparisonFloat) {
62   auto s1 = Scalar(23.0f);
63   auto s2 = Scalar(46.0f);
64   ASSERT_TRUE(s1 < s2);
65   ASSERT_TRUE(s1 <= s2);
66   ASSERT_TRUE(s2 > s1);
67   ASSERT_TRUE(s2 >= s1);
68 }
69 
CheckConversion(T val)70 template <typename T> static void CheckConversion(T val) {
71   SCOPED_TRACE("val = " + std::to_string(val));
72   EXPECT_EQ((signed char)val, Scalar(val).SChar());
73   EXPECT_EQ((unsigned char)val, Scalar(val).UChar());
74   EXPECT_EQ((short)val, Scalar(val).SShort());
75   EXPECT_EQ((unsigned short)val, Scalar(val).UShort());
76   EXPECT_EQ((int)val, Scalar(val).SInt());
77   EXPECT_EQ((unsigned)val, Scalar(val).UInt());
78   EXPECT_EQ((long)val, Scalar(val).SLong());
79   EXPECT_EQ((unsigned long)val, Scalar(val).ULong());
80   EXPECT_EQ((long long)val, Scalar(val).SLongLong());
81   EXPECT_EQ((unsigned long long)val, Scalar(val).ULongLong());
82   EXPECT_NEAR((float)val, Scalar(val).Float(), std::abs(val / 1e6));
83   EXPECT_NEAR((double)val, Scalar(val).Double(), std::abs(val / 1e12));
84   EXPECT_NEAR((long double)val, Scalar(val).LongDouble(), std::abs(val / 1e12));
85 }
86 
TEST(ScalarTest,Getters)87 TEST(ScalarTest, Getters) {
88   CheckConversion<int>(0x87654321);
89   CheckConversion<unsigned int>(0x87654321u);
90   CheckConversion<long>(0x87654321l);
91   CheckConversion<unsigned long>(0x87654321ul);
92   CheckConversion<long long>(0x8765432112345678ll);
93   CheckConversion<unsigned long long>(0x8765432112345678ull);
94   CheckConversion<float>(42.25f);
95   CheckConversion<double>(42.25);
96   CheckConversion<long double>(42.25L);
97 
98   EXPECT_EQ(APInt(128, 1) << 70, Scalar(std::pow(2.0f, 70.0f)).SInt128(APInt()));
99   EXPECT_EQ(APInt(128, -1, true) << 70,
100             Scalar(-std::pow(2.0f, 70.0f)).SInt128(APInt()));
101   EXPECT_EQ(APInt(128, 1) << 70,
102             Scalar(std::pow(2.0f, 70.0f)).UInt128(APInt()));
103   EXPECT_EQ(APInt(128, 0), Scalar(-std::pow(2.0f, 70.0f)).UInt128(APInt()));
104 
105   EXPECT_EQ(APInt(128, 1) << 70, Scalar(std::pow(2.0, 70.0)).SInt128(APInt()));
106   EXPECT_EQ(APInt(128, -1, true) << 70,
107             Scalar(-std::pow(2.0, 70.0)).SInt128(APInt()));
108   EXPECT_EQ(APInt(128, 1) << 70, Scalar(std::pow(2.0, 70.0)).UInt128(APInt()));
109   EXPECT_EQ(APInt(128, 0), Scalar(-std::pow(2.0, 70.0)).UInt128(APInt()));
110 }
111 
TEST(ScalarTest,RightShiftOperator)112 TEST(ScalarTest, RightShiftOperator) {
113   int a = 0x00001000;
114   int b = 0xFFFFFFFF;
115   int c = 4;
116   Scalar a_scalar(a);
117   Scalar b_scalar(b);
118   Scalar c_scalar(c);
119   ASSERT_EQ(a >> c, a_scalar >> c_scalar);
120   ASSERT_EQ(b >> c, b_scalar >> c_scalar);
121 }
122 
TEST(ScalarTest,GetBytes)123 TEST(ScalarTest, GetBytes) {
124   uint8_t Storage[256];
125   int a = 0x01020304;
126   long long b = 0x0102030405060708LL;
127   float c = 1234567.89e32f;
128   double d = 1234567.89e42;
129   char e[16] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16};
130   char f[32] = {1,  2,  3,  4,  5,  6,  7,  8,  9,  10, 11, 12, 13, 14, 15, 16,
131                 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32};
132   Scalar a_scalar(a);
133   Scalar b_scalar(b);
134   Scalar c_scalar(c);
135   Scalar d_scalar(d);
136   Scalar e_scalar;
137   Scalar f_scalar;
138   DataExtractor e_data(e, sizeof(e), endian::InlHostByteOrder(),
139                        sizeof(void *));
140   DataExtractor f_data(f, sizeof(f), endian::InlHostByteOrder(),
141                        sizeof(void *));
142   a_scalar.GetBytes(Storage);
143   ASSERT_EQ(0, memcmp(&a, Storage, sizeof(a)));
144   b_scalar.GetBytes(Storage);
145   ASSERT_EQ(0, memcmp(&b, Storage, sizeof(b)));
146   c_scalar.GetBytes(Storage);
147   ASSERT_EQ(0, memcmp(&c, Storage, sizeof(c)));
148   d_scalar.GetBytes(Storage);
149   ASSERT_EQ(0, memcmp(&d, Storage, sizeof(d)));
150   ASSERT_THAT_ERROR(
151       e_scalar.SetValueFromData(e_data, lldb::eEncodingUint, sizeof(e))
152           .ToError(),
153       llvm::Succeeded());
154   e_scalar.GetBytes(Storage);
155   ASSERT_EQ(0, memcmp(e, Storage, sizeof(e)));
156   ASSERT_THAT_ERROR(
157       f_scalar.SetValueFromData(f_data, lldb::eEncodingUint, sizeof(f))
158           .ToError(),
159       llvm::Succeeded());
160   f_scalar.GetBytes(Storage);
161   ASSERT_EQ(0, memcmp(f, Storage, sizeof(f)));
162 }
163 
TEST(ScalarTest,SetValueFromData)164 TEST(ScalarTest, SetValueFromData) {
165   uint8_t a[] = {1, 2, 3, 4};
166   Scalar s;
167   ASSERT_THAT_ERROR(
168       s.SetValueFromData(
169            DataExtractor(a, sizeof(a), lldb::eByteOrderLittle, sizeof(void *)),
170            lldb::eEncodingSint, sizeof(a))
171           .ToError(),
172       llvm::Succeeded());
173   EXPECT_EQ(0x04030201, s);
174   ASSERT_THAT_ERROR(
175       s.SetValueFromData(
176            DataExtractor(a, sizeof(a), lldb::eByteOrderBig, sizeof(void *)),
177            lldb::eEncodingSint, sizeof(a))
178           .ToError(),
179       llvm::Succeeded());
180   EXPECT_EQ(0x01020304, s);
181 }
182 
TEST(ScalarTest,CastOperations)183 TEST(ScalarTest, CastOperations) {
184   long long a = 0xf1f2f3f4f5f6f7f8LL;
185   Scalar a_scalar(a);
186   EXPECT_EQ((signed char)a, a_scalar.SChar());
187   EXPECT_EQ((unsigned char)a, a_scalar.UChar());
188   EXPECT_EQ((signed short)a, a_scalar.SShort());
189   EXPECT_EQ((unsigned short)a, a_scalar.UShort());
190   EXPECT_EQ((signed int)a, a_scalar.SInt());
191   EXPECT_EQ((unsigned int)a, a_scalar.UInt());
192   EXPECT_EQ((signed long)a, a_scalar.SLong());
193   EXPECT_EQ((unsigned long)a, a_scalar.ULong());
194   EXPECT_EQ((signed long long)a, a_scalar.SLongLong());
195   EXPECT_EQ((unsigned long long)a, a_scalar.ULongLong());
196 
197   int a2 = 23;
198   Scalar a2_scalar(a2);
199   EXPECT_EQ((float)a2, a2_scalar.Float());
200   EXPECT_EQ((double)a2, a2_scalar.Double());
201   EXPECT_EQ((long double)a2, a2_scalar.LongDouble());
202 
203   EXPECT_EQ(std::numeric_limits<unsigned int>::min(), Scalar(-1.0f).UInt());
204   EXPECT_EQ(std::numeric_limits<unsigned int>::max(), Scalar(1e11f).UInt());
205   EXPECT_EQ(std::numeric_limits<unsigned long long>::min(),
206             Scalar(-1.0).ULongLong());
207   EXPECT_EQ(std::numeric_limits<unsigned long long>::max(),
208             Scalar(1e22).ULongLong());
209 
210   EXPECT_EQ(std::numeric_limits<int>::min(), Scalar(-1e11f).SInt());
211   EXPECT_EQ(std::numeric_limits<int>::max(), Scalar(1e11f).SInt());
212   EXPECT_EQ(std::numeric_limits<long long>::min(), Scalar(-1e22).SLongLong());
213   EXPECT_EQ(std::numeric_limits<long long>::max(), Scalar(1e22).SLongLong());
214 }
215 
TEST(ScalarTest,ExtractBitfield)216 TEST(ScalarTest, ExtractBitfield) {
217   uint32_t len = sizeof(long long) * 8;
218 
219   long long a1 = 0xf1f2f3f4f5f6f7f8LL;
220   long long b1 = 0xff1f2f3f4f5f6f7fLL;
221   Scalar s_scalar(a1);
222   ASSERT_TRUE(s_scalar.ExtractBitfield(0, 0));
223   EXPECT_EQ(s_scalar, a1);
224   ASSERT_TRUE(s_scalar.ExtractBitfield(len, 0));
225   EXPECT_EQ(s_scalar, a1);
226   ASSERT_TRUE(s_scalar.ExtractBitfield(len - 4, 4));
227   EXPECT_EQ(s_scalar, b1);
228 
229   unsigned long long a2 = 0xf1f2f3f4f5f6f7f8ULL;
230   unsigned long long b2 = 0x0f1f2f3f4f5f6f7fULL;
231   Scalar u_scalar(a2);
232   ASSERT_TRUE(u_scalar.ExtractBitfield(0, 0));
233   EXPECT_EQ(u_scalar, a2);
234   ASSERT_TRUE(u_scalar.ExtractBitfield(len, 0));
235   EXPECT_EQ(u_scalar, a2);
236   ASSERT_TRUE(u_scalar.ExtractBitfield(len - 4, 4));
237   EXPECT_EQ(u_scalar, b2);
238 }
239 
ScalarGetValue(T value)240 template <typename T> static std::string ScalarGetValue(T value) {
241   StreamString stream;
242   Scalar(value).GetValue(&stream, false);
243   return std::string(stream.GetString());
244 }
245 
TEST(ScalarTest,GetValue)246 TEST(ScalarTest, GetValue) {
247   EXPECT_EQ("12345", ScalarGetValue<signed short>(12345));
248   EXPECT_EQ("-12345", ScalarGetValue<signed short>(-12345));
249   EXPECT_EQ("12345", ScalarGetValue<unsigned short>(12345));
250   EXPECT_EQ(std::to_string(std::numeric_limits<unsigned short>::max()),
251             ScalarGetValue(std::numeric_limits<unsigned short>::max()));
252 
253   EXPECT_EQ("12345", ScalarGetValue<signed int>(12345));
254   EXPECT_EQ("-12345", ScalarGetValue<signed int>(-12345));
255   EXPECT_EQ("12345", ScalarGetValue<unsigned int>(12345));
256   EXPECT_EQ(std::to_string(std::numeric_limits<unsigned int>::max()),
257             ScalarGetValue(std::numeric_limits<unsigned int>::max()));
258 
259   EXPECT_EQ("12345678", ScalarGetValue<signed long>(12345678L));
260   EXPECT_EQ("-12345678", ScalarGetValue<signed long>(-12345678L));
261   EXPECT_EQ("12345678", ScalarGetValue<unsigned long>(12345678UL));
262   EXPECT_EQ(std::to_string(std::numeric_limits<unsigned long>::max()),
263             ScalarGetValue(std::numeric_limits<unsigned long>::max()));
264 
265   EXPECT_EQ("1234567890123", ScalarGetValue<signed long long>(1234567890123LL));
266   EXPECT_EQ("-1234567890123",
267             ScalarGetValue<signed long long>(-1234567890123LL));
268   EXPECT_EQ("1234567890123",
269             ScalarGetValue<unsigned long long>(1234567890123ULL));
270   EXPECT_EQ(std::to_string(std::numeric_limits<unsigned long long>::max()),
271             ScalarGetValue(std::numeric_limits<unsigned long long>::max()));
272 }
273 
TEST(ScalarTest,LongLongAssigmentOperator)274 TEST(ScalarTest, LongLongAssigmentOperator) {
275   Scalar ull;
276   ull = std::numeric_limits<unsigned long long>::max();
277   EXPECT_EQ(std::numeric_limits<unsigned long long>::max(), ull.ULongLong());
278 
279   Scalar sll;
280   sll = std::numeric_limits<signed long long>::max();
281   EXPECT_EQ(std::numeric_limits<signed long long>::max(), sll.SLongLong());
282 }
283 
TEST(ScalarTest,Division)284 TEST(ScalarTest, Division) {
285   Scalar lhs(5.0);
286   Scalar rhs(2.0);
287   Scalar r = lhs / rhs;
288   EXPECT_TRUE(r.IsValid());
289   EXPECT_EQ(r, Scalar(2.5));
290 }
291 
TEST(ScalarTest,Promotion)292 TEST(ScalarTest, Promotion) {
293   Scalar a(47);
294   EXPECT_TRUE(a.IntegralPromote(64, true));
295   EXPECT_TRUE(a.IsSigned());
296   EXPECT_EQ(APInt(64, 47), a.UInt128(APInt()));
297 
298   EXPECT_FALSE(a.IntegralPromote(32, true));
299   EXPECT_FALSE(a.IntegralPromote(32, false));
300   EXPECT_TRUE(a.IsSigned());
301 
302   EXPECT_TRUE(a.IntegralPromote(64, false));
303   EXPECT_FALSE(a.IsSigned());
304   EXPECT_EQ(APInt(64, 47), a.UInt128(APInt()));
305 
306   EXPECT_FALSE(a.IntegralPromote(64, true));
307 
308   EXPECT_TRUE(a.FloatPromote(APFloat::IEEEdouble()));
309   EXPECT_EQ(Scalar::e_float, a.GetType());
310   EXPECT_EQ(47.0, a.Double());
311 
312   EXPECT_FALSE(a.FloatPromote(APFloat::IEEEsingle()));
313   EXPECT_TRUE(a.FloatPromote(APFloat::x87DoubleExtended()));
314   EXPECT_EQ(47.0L, a.LongDouble());
315 }
316 
TEST(ScalarTest,SetValueFromCString)317 TEST(ScalarTest, SetValueFromCString) {
318   Scalar a;
319 
320   EXPECT_THAT_ERROR(
321       a.SetValueFromCString("1234567890123", lldb::eEncodingUint, 8).ToError(),
322       Succeeded());
323   EXPECT_EQ(1234567890123ull, a);
324 
325   EXPECT_THAT_ERROR(
326       a.SetValueFromCString("-1234567890123", lldb::eEncodingSint, 8).ToError(),
327       Succeeded());
328   EXPECT_EQ(-1234567890123ll, a);
329 
330   EXPECT_THAT_ERROR(
331       a.SetValueFromCString("asdf", lldb::eEncodingSint, 8).ToError(),
332       Failed());
333   EXPECT_THAT_ERROR(
334       a.SetValueFromCString("asdf", lldb::eEncodingUint, 8).ToError(),
335       Failed());
336   EXPECT_THAT_ERROR(
337       a.SetValueFromCString("1234567890123", lldb::eEncodingUint, 4).ToError(),
338       Failed());
339   EXPECT_THAT_ERROR(a.SetValueFromCString("123456789012345678901234567890",
340                                           lldb::eEncodingUint, 8)
341                         .ToError(),
342                     Failed());
343   EXPECT_THAT_ERROR(
344       a.SetValueFromCString("-123", lldb::eEncodingUint, 8).ToError(),
345       Failed());
346   EXPECT_THAT_ERROR(
347       a.SetValueFromCString("-2147483648", lldb::eEncodingSint, 4).ToError(),
348       Succeeded());
349   EXPECT_EQ(-2147483648, a);
350   EXPECT_THAT_ERROR(
351       a.SetValueFromCString("-2147483649", lldb::eEncodingSint, 4).ToError(),
352       Failed());
353   EXPECT_THAT_ERROR(
354       a.SetValueFromCString("47.25", lldb::eEncodingIEEE754, 4).ToError(),
355       Succeeded());
356   EXPECT_EQ(47.25f, a);
357   EXPECT_THAT_ERROR(
358       a.SetValueFromCString("asdf", lldb::eEncodingIEEE754, 4).ToError(),
359       Failed());
360 }
361 
TEST(ScalarTest,APIntConstructor)362 TEST(ScalarTest, APIntConstructor) {
363   for (auto &width : {8, 16, 32}) {
364     Scalar A(APInt(width, 24));
365     EXPECT_TRUE(A.IsSigned());
366     EXPECT_EQ(A.GetType(), Scalar::e_int);
367     EXPECT_EQ(APInt(width, 24), A.UInt128(APInt()));
368   }
369 }
370 
TEST(ScalarTest,Scalar_512)371 TEST(ScalarTest, Scalar_512) {
372   Scalar Z(APInt(512, 0));
373   ASSERT_TRUE(Z.IsZero());
374   Z.MakeUnsigned();
375   ASSERT_TRUE(Z.IsZero());
376 
377   Scalar S(APInt(512, 2000));
378   ASSERT_STREQ(S.GetTypeAsCString(), "int");
379 
380   ASSERT_TRUE(S.MakeUnsigned());
381   EXPECT_EQ(S.GetType(), Scalar::e_int);
382   EXPECT_FALSE(S.IsSigned());
383   ASSERT_STREQ(S.GetTypeAsCString(), "int");
384   EXPECT_EQ(S.GetByteSize(), 64U);
385 
386   ASSERT_TRUE(S.MakeSigned());
387   EXPECT_EQ(S.GetType(), Scalar::e_int);
388   EXPECT_TRUE(S.IsSigned());
389   EXPECT_EQ(S.GetByteSize(), 64U);
390 }
391 
TEST(ScalarTest,TruncOrExtendTo)392 TEST(ScalarTest, TruncOrExtendTo) {
393   Scalar S(0xffff);
394   S.TruncOrExtendTo(12, true);
395   EXPECT_EQ(S.UInt128(APInt()), APInt(12, 0xfffu));
396   S.TruncOrExtendTo(20, true);
397   EXPECT_EQ(S.UInt128(APInt()), APInt(20, 0xfffffu));
398   S.TruncOrExtendTo(24, false);
399   EXPECT_EQ(S.UInt128(APInt()), APInt(24, 0x0fffffu));
400   S.TruncOrExtendTo(16, false);
401   EXPECT_EQ(S.UInt128(APInt()), APInt(16, 0xffffu));
402 }
403