xref: /aosp_15_r20/external/libbrillo/brillo/any_internal_impl_test.cc (revision 1a96fba65179ea7d3f56207137718607415c5953)
1*1a96fba6SXin Li // Copyright 2014 The Chromium OS Authors. All rights reserved.
2*1a96fba6SXin Li // Use of this source code is governed by a BSD-style license that can be
3*1a96fba6SXin Li // found in the LICENSE file.
4*1a96fba6SXin Li 
5*1a96fba6SXin Li #include <string>
6*1a96fba6SXin Li 
7*1a96fba6SXin Li #include <brillo/any.h>
8*1a96fba6SXin Li #include <gtest/gtest.h>
9*1a96fba6SXin Li 
10*1a96fba6SXin Li using brillo::internal_details::Buffer;
11*1a96fba6SXin Li using brillo::GetTypeTag;
12*1a96fba6SXin Li 
TEST(Buffer,Empty)13*1a96fba6SXin Li TEST(Buffer, Empty) {
14*1a96fba6SXin Li   Buffer buffer;
15*1a96fba6SXin Li   EXPECT_TRUE(buffer.IsEmpty());
16*1a96fba6SXin Li   EXPECT_EQ(Buffer::kExternal, buffer.storage_);
17*1a96fba6SXin Li   EXPECT_EQ(nullptr, buffer.GetDataPtr());
18*1a96fba6SXin Li }
19*1a96fba6SXin Li 
TEST(Buffer,Store_Int)20*1a96fba6SXin Li TEST(Buffer, Store_Int) {
21*1a96fba6SXin Li   Buffer buffer;
22*1a96fba6SXin Li   buffer.Assign(2);
23*1a96fba6SXin Li   EXPECT_FALSE(buffer.IsEmpty());
24*1a96fba6SXin Li   EXPECT_EQ(Buffer::kContained, buffer.storage_);
25*1a96fba6SXin Li   EXPECT_STREQ(GetTypeTag<int>(), buffer.GetDataPtr()->GetTypeTag());
26*1a96fba6SXin Li }
27*1a96fba6SXin Li 
TEST(Buffer,Store_Double)28*1a96fba6SXin Li TEST(Buffer, Store_Double) {
29*1a96fba6SXin Li   Buffer buffer;
30*1a96fba6SXin Li   buffer.Assign(2.3);
31*1a96fba6SXin Li   EXPECT_FALSE(buffer.IsEmpty());
32*1a96fba6SXin Li   EXPECT_EQ(Buffer::kContained, buffer.storage_);
33*1a96fba6SXin Li   EXPECT_STREQ(GetTypeTag<double>(), buffer.GetDataPtr()->GetTypeTag());
34*1a96fba6SXin Li }
35*1a96fba6SXin Li 
TEST(Buffer,Store_Pointers)36*1a96fba6SXin Li TEST(Buffer, Store_Pointers) {
37*1a96fba6SXin Li   Buffer buffer;
38*1a96fba6SXin Li   // nullptr
39*1a96fba6SXin Li   buffer.Assign(nullptr);
40*1a96fba6SXin Li   EXPECT_FALSE(buffer.IsEmpty());
41*1a96fba6SXin Li   EXPECT_EQ(Buffer::kContained, buffer.storage_);
42*1a96fba6SXin Li   EXPECT_STREQ(GetTypeTag<std::nullptr_t>(),
43*1a96fba6SXin Li                buffer.GetDataPtr()->GetTypeTag());
44*1a96fba6SXin Li 
45*1a96fba6SXin Li   // char *
46*1a96fba6SXin Li   buffer.Assign("abcd");
47*1a96fba6SXin Li   EXPECT_FALSE(buffer.IsEmpty());
48*1a96fba6SXin Li   EXPECT_EQ(Buffer::kContained, buffer.storage_);
49*1a96fba6SXin Li   EXPECT_STREQ(GetTypeTag<const char*>(), buffer.GetDataPtr()->GetTypeTag());
50*1a96fba6SXin Li 
51*1a96fba6SXin Li   // pointer to non-trivial object
52*1a96fba6SXin Li   class NonTrivial {
53*1a96fba6SXin Li    public:
54*1a96fba6SXin Li     virtual ~NonTrivial() {}
55*1a96fba6SXin Li   } non_trivial;
56*1a96fba6SXin Li   buffer.Assign(&non_trivial);
57*1a96fba6SXin Li   EXPECT_FALSE(buffer.IsEmpty());
58*1a96fba6SXin Li   EXPECT_EQ(Buffer::kContained, buffer.storage_);
59*1a96fba6SXin Li   EXPECT_STREQ(GetTypeTag<NonTrivial*>(), buffer.GetDataPtr()->GetTypeTag());
60*1a96fba6SXin Li }
61*1a96fba6SXin Li 
TEST(Buffer,Store_NonTrivialObjects)62*1a96fba6SXin Li TEST(Buffer, Store_NonTrivialObjects) {
63*1a96fba6SXin Li   class NonTrivial {
64*1a96fba6SXin Li    public:
65*1a96fba6SXin Li     virtual ~NonTrivial() {}
66*1a96fba6SXin Li   } non_trivial;
67*1a96fba6SXin Li   Buffer buffer;
68*1a96fba6SXin Li   buffer.Assign(non_trivial);
69*1a96fba6SXin Li   EXPECT_FALSE(buffer.IsEmpty());
70*1a96fba6SXin Li   EXPECT_EQ(Buffer::kExternal, buffer.storage_);
71*1a96fba6SXin Li   EXPECT_STREQ(GetTypeTag<NonTrivial>(), buffer.GetDataPtr()->GetTypeTag());
72*1a96fba6SXin Li }
73*1a96fba6SXin Li 
TEST(Buffer,Store_Objects)74*1a96fba6SXin Li TEST(Buffer, Store_Objects) {
75*1a96fba6SXin Li   Buffer buffer;
76*1a96fba6SXin Li 
77*1a96fba6SXin Li   struct Small {
78*1a96fba6SXin Li     double d;
79*1a96fba6SXin Li   } small = {};
80*1a96fba6SXin Li   buffer.Assign(small);
81*1a96fba6SXin Li   EXPECT_FALSE(buffer.IsEmpty());
82*1a96fba6SXin Li   EXPECT_EQ(Buffer::kContained, buffer.storage_);
83*1a96fba6SXin Li   EXPECT_STREQ(GetTypeTag<Small>(), buffer.GetDataPtr()->GetTypeTag());
84*1a96fba6SXin Li 
85*1a96fba6SXin Li   struct Large {
86*1a96fba6SXin Li     char c[20];
87*1a96fba6SXin Li   } large = {};
88*1a96fba6SXin Li   buffer.Assign(large);
89*1a96fba6SXin Li   EXPECT_FALSE(buffer.IsEmpty());
90*1a96fba6SXin Li   EXPECT_EQ(Buffer::kExternal, buffer.storage_);
91*1a96fba6SXin Li   EXPECT_STREQ(GetTypeTag<Large>(), buffer.GetDataPtr()->GetTypeTag());
92*1a96fba6SXin Li }
93*1a96fba6SXin Li 
TEST(Buffer,Copy)94*1a96fba6SXin Li TEST(Buffer, Copy) {
95*1a96fba6SXin Li   Buffer buffer1;
96*1a96fba6SXin Li   Buffer buffer2;
97*1a96fba6SXin Li 
98*1a96fba6SXin Li   buffer1.Assign(30);
99*1a96fba6SXin Li   buffer1.CopyTo(&buffer2);
100*1a96fba6SXin Li   EXPECT_FALSE(buffer1.IsEmpty());
101*1a96fba6SXin Li   EXPECT_FALSE(buffer2.IsEmpty());
102*1a96fba6SXin Li   EXPECT_STREQ(GetTypeTag<int>(), buffer1.GetDataPtr()->GetTypeTag());
103*1a96fba6SXin Li   EXPECT_STREQ(GetTypeTag<int>(), buffer2.GetDataPtr()->GetTypeTag());
104*1a96fba6SXin Li   EXPECT_EQ(30, buffer1.GetData<int>());
105*1a96fba6SXin Li   EXPECT_EQ(30, buffer2.GetData<int>());
106*1a96fba6SXin Li 
107*1a96fba6SXin Li   buffer1.Assign(std::string("abc"));
108*1a96fba6SXin Li   buffer1.CopyTo(&buffer2);
109*1a96fba6SXin Li   EXPECT_FALSE(buffer1.IsEmpty());
110*1a96fba6SXin Li   EXPECT_FALSE(buffer2.IsEmpty());
111*1a96fba6SXin Li   EXPECT_STREQ(GetTypeTag<std::string>(), buffer1.GetDataPtr()->GetTypeTag());
112*1a96fba6SXin Li   EXPECT_STREQ(GetTypeTag<std::string>(), buffer2.GetDataPtr()->GetTypeTag());
113*1a96fba6SXin Li   EXPECT_EQ("abc", buffer1.GetData<std::string>());
114*1a96fba6SXin Li   EXPECT_EQ("abc", buffer2.GetData<std::string>());
115*1a96fba6SXin Li }
116*1a96fba6SXin Li 
TEST(Buffer,Move)117*1a96fba6SXin Li TEST(Buffer, Move) {
118*1a96fba6SXin Li   // Move operations essentially leave the source object in a state that is
119*1a96fba6SXin Li   // guaranteed to be safe for reuse or destruction. There is no other explicit
120*1a96fba6SXin Li   // guarantees on the exact state of the source after move (e.g. that the
121*1a96fba6SXin Li   // source Any will be Empty after the move is complete).
122*1a96fba6SXin Li   Buffer buffer1;
123*1a96fba6SXin Li   Buffer buffer2;
124*1a96fba6SXin Li 
125*1a96fba6SXin Li   buffer1.Assign(30);
126*1a96fba6SXin Li   buffer1.MoveTo(&buffer2);
127*1a96fba6SXin Li   // Contained types aren't flushed, so the source Any doesn't become empty.
128*1a96fba6SXin Li   // The contained value is just moved, but for scalars this just copies
129*1a96fba6SXin Li   // the data and any retains the actual type.
130*1a96fba6SXin Li   EXPECT_FALSE(buffer1.IsEmpty());
131*1a96fba6SXin Li   EXPECT_FALSE(buffer2.IsEmpty());
132*1a96fba6SXin Li   EXPECT_STREQ(GetTypeTag<int>(), buffer2.GetDataPtr()->GetTypeTag());
133*1a96fba6SXin Li   EXPECT_EQ(30, buffer2.GetData<int>());
134*1a96fba6SXin Li 
135*1a96fba6SXin Li   buffer1.Assign(std::string("abc"));
136*1a96fba6SXin Li   buffer1.MoveTo(&buffer2);
137*1a96fba6SXin Li   // External types are moved by just moving the pointer value from src to dest.
138*1a96fba6SXin Li   // This will make the source object effectively "Empty".
139*1a96fba6SXin Li   EXPECT_TRUE(buffer1.IsEmpty());
140*1a96fba6SXin Li   EXPECT_FALSE(buffer2.IsEmpty());
141*1a96fba6SXin Li   EXPECT_STREQ(GetTypeTag<std::string>(), buffer2.GetDataPtr()->GetTypeTag());
142*1a96fba6SXin Li   EXPECT_EQ("abc", buffer2.GetData<std::string>());
143*1a96fba6SXin Li }
144