xref: /llvm-project/clang/unittests/AST/ByteCode/BitcastBuffer.cpp (revision 12ca72ba7f11fb880794a37cffdea5f47e3062f4)
1*12ca72baSTimm Bäder #include "../../../lib/AST/ByteCode/BitcastBuffer.h"
2*12ca72baSTimm Bäder #include "clang/AST/ASTContext.h"
3*12ca72baSTimm Bäder #include "gtest/gtest.h"
4*12ca72baSTimm Bäder #include <bitset>
5*12ca72baSTimm Bäder #include <cassert>
6*12ca72baSTimm Bäder #include <cmath>
7*12ca72baSTimm Bäder #include <memory>
8*12ca72baSTimm Bäder #include <string>
9*12ca72baSTimm Bäder 
10*12ca72baSTimm Bäder using namespace clang;
11*12ca72baSTimm Bäder using namespace clang::interp;
12*12ca72baSTimm Bäder 
13*12ca72baSTimm Bäder TEST(BitcastBuffer, PushData) {
14*12ca72baSTimm Bäder   BitcastBuffer Buff1(Bytes(sizeof(int)).toBits());
15*12ca72baSTimm Bäder 
16*12ca72baSTimm Bäder   const unsigned V = 0xCAFEBABE;
17*12ca72baSTimm Bäder   Bits VSize = Bytes(sizeof(V)).toBits();
18*12ca72baSTimm Bäder   std::byte Data[sizeof(V)];
19*12ca72baSTimm Bäder   std::memcpy(Data, &V, sizeof(V));
20*12ca72baSTimm Bäder 
21*12ca72baSTimm Bäder   Endian HostEndianness =
22*12ca72baSTimm Bäder       llvm::sys::IsLittleEndianHost ? Endian::Little : Endian::Big;
23*12ca72baSTimm Bäder 
24*12ca72baSTimm Bäder   Buff1.pushData(Data, Bits::zero(), VSize, HostEndianness);
25*12ca72baSTimm Bäder 
26*12ca72baSTimm Bäder   // The buffer is in host-endianness.
27*12ca72baSTimm Bäder   if (llvm::sys::IsLittleEndianHost) {
28*12ca72baSTimm Bäder     ASSERT_EQ(Buff1.Data[0], std::byte{0xbe});
29*12ca72baSTimm Bäder     ASSERT_EQ(Buff1.Data[1], std::byte{0xba});
30*12ca72baSTimm Bäder     ASSERT_EQ(Buff1.Data[2], std::byte{0xfe});
31*12ca72baSTimm Bäder     ASSERT_EQ(Buff1.Data[3], std::byte{0xca});
32*12ca72baSTimm Bäder   } else {
33*12ca72baSTimm Bäder     ASSERT_EQ(Buff1.Data[0], std::byte{0xca});
34*12ca72baSTimm Bäder     ASSERT_EQ(Buff1.Data[1], std::byte{0xfe});
35*12ca72baSTimm Bäder     ASSERT_EQ(Buff1.Data[2], std::byte{0xba});
36*12ca72baSTimm Bäder     ASSERT_EQ(Buff1.Data[3], std::byte{0xbe});
37*12ca72baSTimm Bäder   }
38*12ca72baSTimm Bäder 
39*12ca72baSTimm Bäder   {
40*12ca72baSTimm Bäder     unsigned V2;
41*12ca72baSTimm Bäder     auto D = Buff1.copyBits(Bits::zero(), VSize, VSize, Endian::Little);
42*12ca72baSTimm Bäder     std::memcpy(&V2, D.get(), sizeof(V));
43*12ca72baSTimm Bäder     ASSERT_EQ(V, V2);
44*12ca72baSTimm Bäder 
45*12ca72baSTimm Bäder     D = Buff1.copyBits(Bits::zero(), VSize, VSize, Endian::Big);
46*12ca72baSTimm Bäder     std::memcpy(&V2, D.get(), sizeof(V));
47*12ca72baSTimm Bäder     ASSERT_EQ(V, V2);
48*12ca72baSTimm Bäder   }
49*12ca72baSTimm Bäder 
50*12ca72baSTimm Bäder   BitcastBuffer Buff2(Bytes(sizeof(int)).toBits());
51*12ca72baSTimm Bäder   {
52*12ca72baSTimm Bäder     short s1 = 0xCAFE;
53*12ca72baSTimm Bäder     short s2 = 0xBABE;
54*12ca72baSTimm Bäder     std::byte sdata[2];
55*12ca72baSTimm Bäder 
56*12ca72baSTimm Bäder     std::memcpy(sdata, &s1, sizeof(s1));
57*12ca72baSTimm Bäder     Buff2.pushData(sdata, Bits::zero(), Bits(sizeof(s1) * 8), HostEndianness);
58*12ca72baSTimm Bäder     std::memcpy(sdata, &s2, sizeof(s2));
59*12ca72baSTimm Bäder     Buff2.pushData(sdata, Bits(sizeof(s1) * 8), Bits(sizeof(s2) * 8),
60*12ca72baSTimm Bäder                    HostEndianness);
61*12ca72baSTimm Bäder   }
62*12ca72baSTimm Bäder 
63*12ca72baSTimm Bäder   if (llvm::sys::IsLittleEndianHost) {
64*12ca72baSTimm Bäder     ASSERT_EQ(Buff2.Data[0], std::byte{0xfe});
65*12ca72baSTimm Bäder     ASSERT_EQ(Buff2.Data[1], std::byte{0xca});
66*12ca72baSTimm Bäder     ASSERT_EQ(Buff2.Data[2], std::byte{0xbe});
67*12ca72baSTimm Bäder     ASSERT_EQ(Buff2.Data[3], std::byte{0xba});
68*12ca72baSTimm Bäder   } else {
69*12ca72baSTimm Bäder     ASSERT_EQ(Buff2.Data[0], std::byte{0xba});
70*12ca72baSTimm Bäder     ASSERT_EQ(Buff2.Data[1], std::byte{0xbe});
71*12ca72baSTimm Bäder     ASSERT_EQ(Buff2.Data[2], std::byte{0xca});
72*12ca72baSTimm Bäder     ASSERT_EQ(Buff2.Data[3], std::byte{0xfe});
73*12ca72baSTimm Bäder   }
74*12ca72baSTimm Bäder 
75*12ca72baSTimm Bäder   {
76*12ca72baSTimm Bäder     unsigned V;
77*12ca72baSTimm Bäder     auto D = Buff2.copyBits(Bits::zero(), Bits(sizeof(V) * 8),
78*12ca72baSTimm Bäder                             Bits(sizeof(V) * 8), Endian::Little);
79*12ca72baSTimm Bäder     std::memcpy(&V, D.get(), sizeof(V));
80*12ca72baSTimm Bäder     ASSERT_EQ(V, 0xBABECAFE);
81*12ca72baSTimm Bäder 
82*12ca72baSTimm Bäder     D = Buff2.copyBits(Bits::zero(), Bits(sizeof(V) * 8), Bits(sizeof(V) * 8),
83*12ca72baSTimm Bäder                        Endian::Big);
84*12ca72baSTimm Bäder     std::memcpy(&V, D.get(), sizeof(V));
85*12ca72baSTimm Bäder     ASSERT_EQ(V, 0xBABECAFE);
86*12ca72baSTimm Bäder   }
87*12ca72baSTimm Bäder }
88