1 #include "rde/rde_dictionary_manager.hpp" 2 3 #include <cstring> 4 #include <memory> 5 #include <optional> 6 #include <span> 7 8 #include <gmock/gmock-matchers.h> 9 #include <gmock/gmock.h> 10 #include <gtest/gtest.h> 11 12 namespace bios_bmc_smm_error_logger 13 { 14 namespace rde 15 { 16 17 constexpr std::array<uint8_t, 132> dummyDictionary1{ 18 {0x00, 0x03, 0x02, 0x00, 0x00, 0x00, 0x17, 0x01, 0x00, 0x00, 0x0, 0x0, 19 0xc, 0x0, 0x0, 0xf0, 0xf0, 0xf1, 0x17, 0x1, 0x0, 0x0, 0x0, 0x0, 20 0x0, 0x16, 0x0, 0x5, 0x0, 0xc, 0x84, 0x0, 0x14, 0x0, 0x0, 0x48, 21 0x0, 0x1, 0x0, 0x13, 0x90, 0x0, 0x56, 0x1, 0x0, 0x0, 0x0, 0x0, 22 0x0, 0x3, 0xa3, 0x0, 0x74, 0x2, 0x0, 0x0, 0x0, 0x0, 0x0, 0x16, 23 0xa6, 0x0, 0x34, 0x3, 0x0, 0x0, 0x0, 0x0, 0x0, 0x16, 0xbc, 0x0, 24 0x64, 0x4, 0x0, 0x0, 0x0, 0x0, 0x0, 0x13, 0xd2, 0x0, 0x0, 0x0, 25 0x0, 0x52, 0x0, 0x2, 0x0, 0x0, 0x0, 0x0, 0x74, 0x0, 0x0, 0x0, 26 0x0, 0x0, 0x0, 0xf, 0xe5, 0x0, 0x46, 0x1, 0x0, 0x66, 0x0, 0x3, 27 0x0, 0xb, 0xf4, 0x0, 0x50, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x9, 28 0xff, 0x0, 0x50, 0x1, 0x0, 0x0, 0x0, 0x0, 0x0, 0x7, 0x8, 0x1}}; 29 30 constexpr std::array<uint8_t, 14> dummyDictionary2{ 31 {0x65, 0x0, 0x43, 0x68, 0x69, 0x6c, 0x64, 0x41, 0x72, 0x72, 0x61, 0x79, 32 0x50, 0x72}}; 33 34 class RdeDictionaryManagerTest : public ::testing::Test 35 { 36 protected: 37 uint32_t resourceId = 1; 38 DictionaryManager dm; 39 }; 40 41 TEST_F(RdeDictionaryManagerTest, DictionarySetTest) 42 { 43 // Add a single dictionary. 44 dm.startDictionaryEntry(resourceId, std::span(dummyDictionary1)); 45 EXPECT_THAT(dm.getDictionaryCount(), 0); 46 47 // Mark the dictionary as a valid dictionary. 48 dm.markDataComplete(resourceId); 49 EXPECT_THAT(dm.getDictionaryCount(), 1); 50 51 // Request the dictionary back and verify the data. 52 auto dataOrErr = dm.getDictionary(resourceId); 53 EXPECT_TRUE(dataOrErr); 54 EXPECT_THAT((*dataOrErr).size_bytes(), dummyDictionary1.size()); 55 EXPECT_THAT(memcmp((*dataOrErr).data(), dummyDictionary1.data(), 56 dummyDictionary1.size()), 57 0); 58 } 59 60 TEST_F(RdeDictionaryManagerTest, DictionaryNotSetTest) 61 { 62 // Add a single dictionary. 63 dm.startDictionaryEntry(resourceId, std::span(dummyDictionary1)); 64 EXPECT_THAT(dm.getDictionaryCount(), 0); 65 // Request the dictionary back without marking it complete. Request should 66 // fail. 67 EXPECT_FALSE(dm.getDictionary(resourceId)); 68 } 69 70 TEST_F(RdeDictionaryManagerTest, DictionaryMultiSetTest) 71 { 72 // Creates a dictionary 73 dm.startDictionaryEntry(resourceId, std::span(dummyDictionary1)); 74 EXPECT_THAT(dm.getDictionaryCount(), 0); 75 dm.markDataComplete(resourceId); 76 EXPECT_THAT(dm.getDictionaryCount(), 1); 77 78 // Creates a second dictionary. 79 dm.startDictionaryEntry(annotationResourceId, std::span(dummyDictionary2)); 80 dm.markDataComplete(annotationResourceId); 81 EXPECT_THAT(dm.getDictionaryCount(), 2); 82 83 auto data1OrErr = dm.getDictionary(resourceId); 84 EXPECT_TRUE(data1OrErr); 85 EXPECT_THAT((*data1OrErr).size_bytes(), dummyDictionary1.size()); 86 EXPECT_THAT(memcmp((*data1OrErr).data(), dummyDictionary1.data(), 87 dummyDictionary1.size()), 88 0); 89 90 auto data2OrErr = dm.getDictionary(annotationResourceId); 91 EXPECT_TRUE(data2OrErr); 92 EXPECT_THAT((*data2OrErr).size_bytes(), dummyDictionary2.size()); 93 EXPECT_THAT(memcmp((*data2OrErr).data(), dummyDictionary2.data(), 94 dummyDictionary2.size()), 95 0); 96 } 97 98 TEST_F(RdeDictionaryManagerTest, DictionaryOverwriteTest) 99 { 100 dm.startDictionaryEntry(resourceId, std::span(dummyDictionary2)); 101 102 // Recreate another one on the same location. 103 dm.startDictionaryEntry(resourceId, std::span(dummyDictionary1)); 104 EXPECT_THAT(dm.getDictionaryCount(), 0); 105 dm.markDataComplete(resourceId); 106 EXPECT_THAT(dm.getDictionaryCount(), 1); 107 108 auto dataOrErr = dm.getDictionary(resourceId); 109 EXPECT_TRUE(dataOrErr); 110 EXPECT_THAT((*dataOrErr).size_bytes(), dummyDictionary1.size()); 111 EXPECT_THAT(memcmp((*dataOrErr).data(), dummyDictionary1.data(), 112 dummyDictionary1.size()), 113 0); 114 115 // Recreate another one on the same location. 116 dm.startDictionaryEntry(resourceId, std::span(dummyDictionary2)); 117 EXPECT_THAT(dm.getDictionaryCount(), 0); 118 dm.markDataComplete(resourceId); 119 EXPECT_THAT(dm.getDictionaryCount(), 1); 120 121 auto newDataOrErr = dm.getDictionary(resourceId); 122 EXPECT_TRUE(newDataOrErr); 123 EXPECT_THAT((*newDataOrErr).size_bytes(), dummyDictionary2.size()); 124 EXPECT_THAT(memcmp((*newDataOrErr).data(), dummyDictionary2.data(), 125 dummyDictionary2.size()), 126 0); 127 } 128 129 TEST_F(RdeDictionaryManagerTest, DictionaryAppendDataTest) 130 { 131 // Creates a dictionary 132 dm.startDictionaryEntry(resourceId, std::span(dummyDictionary1)); 133 EXPECT_THAT(dm.getDictionaryCount(), 0); 134 135 // Lets copy the dictionary in two sizes. 136 const uint32_t copySize1 = dummyDictionary2.size() / 2; 137 const uint32_t copySize2 = dummyDictionary2.size() - copySize1; 138 139 // Overwrite on the same location as before. 140 dm.startDictionaryEntry(resourceId, 141 std::span(dummyDictionary2.data(), copySize1)); 142 dm.addDictionaryData( 143 resourceId, std::span(dummyDictionary2.data() + copySize1, copySize2)); 144 dm.markDataComplete(resourceId); 145 EXPECT_THAT(dm.getDictionaryCount(), 1); 146 147 auto dataOrErr = dm.getDictionary(resourceId); 148 EXPECT_TRUE(dataOrErr); 149 EXPECT_THAT((*dataOrErr).size_bytes(), dummyDictionary2.size()); 150 EXPECT_THAT(memcmp((*dataOrErr).data(), dummyDictionary2.data(), 151 dummyDictionary2.size()), 152 0); 153 } 154 155 TEST_F(RdeDictionaryManagerTest, DictionaryOverrideWithAddDataTest) 156 { 157 dm.startDictionaryEntry(resourceId, std::span(dummyDictionary1)); 158 dm.markDataComplete(resourceId); 159 EXPECT_THAT(dm.getDictionaryCount(), 1); 160 161 dm.addDictionaryData(resourceId, std::span(dummyDictionary2)); 162 EXPECT_THAT(dm.getDictionaryCount(), 0); 163 dm.markDataComplete(resourceId); 164 EXPECT_THAT(dm.getDictionaryCount(), 1); 165 } 166 167 TEST_F(RdeDictionaryManagerTest, DictionaryInvalidateTest) 168 { 169 dm.startDictionaryEntry(resourceId, std::span(dummyDictionary1)); 170 dm.markDataComplete(resourceId); 171 EXPECT_THAT(dm.getDictionaryCount(), 1); 172 173 dm.invalidateDictionaries(); 174 EXPECT_THAT(dm.getDictionaryCount(), 0); 175 } 176 177 } // namespace rde 178 } // namespace bios_bmc_smm_error_logger 179