blob: 1bef136cd7cc2efe2a4c11d8524b460ac421cfb4 [file] [log] [blame]
Patrick Venturea82f99e2019-05-24 15:44:35 -07001/**
2 * The goal of these tests is to verify the behavior of all blob commands given
3 * the current state is verificationCompleted. This state is achieved as a out
4 * of verificationStarted.
5 */
6#include "firmware_handler.hpp"
7#include "firmware_unittest.hpp"
8#include "status.hpp"
9#include "util.hpp"
10
11#include <cstdint>
12#include <string>
13#include <vector>
14
15#include <gtest/gtest.h>
16
17namespace ipmi_flash
18{
19namespace
20{
21
Patrick Venture65cdcf02019-05-29 10:18:50 -070022using ::testing::IsEmpty;
Patrick Venturea82f99e2019-05-24 15:44:35 -070023using ::testing::Return;
Patrick Venture6d3a14c2019-05-29 09:24:42 -070024using ::testing::UnorderedElementsAreArray;
Patrick Venturea82f99e2019-05-24 15:44:35 -070025
26/*
27 * There are the following calls (parameters may vary):
28 * canHandleBlob(blob)
29 * getBlobIds
30 * deleteBlob(blob)
31 * stat(blob)
32 * stat(session)
33 * open(blob)
34 * close(session)
35 * writemeta(session)
36 * write(session)
37 * read(session)
38 * commit(session)
39 *
40 * Like the state verificationStarted, there is a file open in
41 * verificationCompleted. This state is transitioned to after a stat() command
42 * indicates a successful verification.
43 */
44
45class FirmwareHandlerVerificationCompletedTest
46 : public IpmiOnlyFirmwareStaticTest
47{
48 protected:
Patrick Venture0c642fd2019-05-24 16:09:29 -070049 void getToVerificationCompleted(VerifyCheckResponses checkResponse)
Patrick Venturea82f99e2019-05-24 15:44:35 -070050 {
Patrick Venture0c642fd2019-05-24 16:09:29 -070051 /* The hash was not sent up, as it's technically optional. Therefore,
52 * there is no active hash file.
53 */
Patrick Venturea82f99e2019-05-24 15:44:35 -070054 EXPECT_CALL(imageMock, open(staticLayoutBlobId)).WillOnce(Return(true));
55 EXPECT_TRUE(handler->open(session, flags, staticLayoutBlobId));
Patrick Venture6fdd02e2019-05-28 13:02:04 -070056 expectedState(FirmwareBlobHandler::UpdateState::uploadInProgress);
57
Patrick Venturea82f99e2019-05-24 15:44:35 -070058 EXPECT_CALL(imageMock, close()).WillRepeatedly(Return());
59 handler->close(session);
Patrick Venture6fdd02e2019-05-28 13:02:04 -070060 expectedState(FirmwareBlobHandler::UpdateState::verificationPending);
Patrick Venturea82f99e2019-05-24 15:44:35 -070061
62 EXPECT_TRUE(handler->open(session, flags, verifyBlobId));
63 EXPECT_CALL(*verifyMockPtr, triggerVerification())
64 .WillOnce(Return(true));
65
66 EXPECT_TRUE(handler->commit(session, {}));
Patrick Venture6fdd02e2019-05-28 13:02:04 -070067 expectedState(FirmwareBlobHandler::UpdateState::verificationStarted);
Patrick Venturea82f99e2019-05-24 15:44:35 -070068
69 EXPECT_CALL(*verifyMockPtr, checkVerificationState())
Patrick Venture0c642fd2019-05-24 16:09:29 -070070 .WillOnce(Return(checkResponse));
Patrick Venturea82f99e2019-05-24 15:44:35 -070071 blobs::BlobMeta meta;
72 EXPECT_TRUE(handler->stat(session, &meta));
Patrick Venture6fdd02e2019-05-28 13:02:04 -070073 expectedState(FirmwareBlobHandler::UpdateState::verificationCompleted);
Patrick Venturea82f99e2019-05-24 15:44:35 -070074 }
75
76 std::uint16_t session = 1;
77 std::uint16_t flags =
78 blobs::OpenFlags::write | FirmwareBlobHandler::UpdateFlags::ipmi;
79};
80
Patrick Venture6d3a14c2019-05-29 09:24:42 -070081/* TODO: deleteBlob(blob) */
82
83/*
84 * canHandleBlob
Patrick Venturea82f99e2019-05-24 15:44:35 -070085 */
Patrick Venture6d3a14c2019-05-29 09:24:42 -070086TEST_F(FirmwareHandlerVerificationCompletedTest,
87 OnVerificationCompleteSuccessUpdateBlobIdNotPresent)
88{
89 /* the uploadBlobId is only added on close() of the verifyBlobId. This is a
90 * consistent behavior with verifyBlobId only added when closing the image
91 * or hash.
92 */
93 getToVerificationCompleted(VerifyCheckResponses::success);
94 EXPECT_FALSE(handler->canHandleBlob(updateBlobId));
95}
96
97TEST_F(FirmwareHandlerVerificationCompletedTest,
98 OnVerificationCompleteFailureUpdateBlobIdNotPresent)
99{
100 getToVerificationCompleted(VerifyCheckResponses::failed);
101 EXPECT_FALSE(handler->canHandleBlob(updateBlobId));
102}
103
104/*
105 * getBlobIds
106 */
107TEST_F(FirmwareHandlerVerificationCompletedTest, GetBlobIdsReturnsExpectedList)
108{
109 getToVerificationCompleted(VerifyCheckResponses::success);
110 std::vector<std::string> expected = {verifyBlobId, hashBlobId,
111 activeImageBlobId, staticLayoutBlobId};
112 EXPECT_THAT(handler->getBlobIds(), UnorderedElementsAreArray(expected));
113}
Patrick Venturea82f99e2019-05-24 15:44:35 -0700114
115/*
116 * stat(blob)
117 */
Patrick Venture0c642fd2019-05-24 16:09:29 -0700118TEST_F(FirmwareHandlerVerificationCompletedTest,
119 StatOnActiveImageReturnsFailure)
120{
121 getToVerificationCompleted(VerifyCheckResponses::success);
122 ASSERT_TRUE(handler->canHandleBlob(activeImageBlobId));
123
124 blobs::BlobMeta meta;
125 EXPECT_FALSE(handler->stat(activeImageBlobId, &meta));
126}
127
Patrick Venturefbf07ff2019-05-29 08:58:45 -0700128TEST_F(FirmwareHandlerVerificationCompletedTest,
129 VerifyActiveHashIdMissingInThisCase)
130{
131 /* The path taken to get to this state never opened the hash blob Id, which
132 * is fine. But let's verify it behaved as intended.
133 */
134 getToVerificationCompleted(VerifyCheckResponses::success);
135 EXPECT_FALSE(handler->canHandleBlob(activeHashBlobId));
136}
137
138/* TODO: Add sufficient warning that you can get to verificationCompleted
139 * without ever opening the image blob id (or the tarball one).
140 *
141 * Although in this case, it's expected that any verification triggered would
142 * certainly fail. So, although it's possible, it's uninteresting.
143 */
144
Patrick Venture0c642fd2019-05-24 16:09:29 -0700145TEST_F(FirmwareHandlerVerificationCompletedTest, StatOnVerifyBlobReturnsFailure)
146{
147 getToVerificationCompleted(VerifyCheckResponses::success);
148 ASSERT_TRUE(handler->canHandleBlob(verifyBlobId));
149
150 blobs::BlobMeta meta;
151 EXPECT_FALSE(handler->stat(verifyBlobId, &meta));
152}
153
154TEST_F(FirmwareHandlerVerificationCompletedTest,
155 StatOnNormalBlobsReturnsSuccess)
156{
157 getToVerificationCompleted(VerifyCheckResponses::success);
158
159 blobs::BlobMeta expected;
160 expected.blobState = FirmwareBlobHandler::UpdateFlags::ipmi;
161 expected.size = 0;
162
163 std::vector<std::string> testBlobs = {staticLayoutBlobId, hashBlobId};
164 for (const auto& blob : testBlobs)
165 {
166 ASSERT_TRUE(handler->canHandleBlob(blob));
167
168 blobs::BlobMeta meta = {};
169 EXPECT_TRUE(handler->stat(blob, &meta));
170 EXPECT_EQ(expected, meta);
171 }
172}
Patrick Venturea82f99e2019-05-24 15:44:35 -0700173
174/*
175 * stat(session) - the verify blobid is open in this state, so stat on that once
176 * completed should have no effect.
Patrick Venture65cdcf02019-05-29 10:18:50 -0700177 */
178
179/*
Patrick Venturea82f99e2019-05-24 15:44:35 -0700180 * open(blob) - all open should fail
Patrick Venturea82f99e2019-05-24 15:44:35 -0700181 */
Patrick Ventureeee71812019-05-29 10:41:04 -0700182TEST_F(FirmwareHandlerVerificationCompletedTest,
183 OpeningAnyBlobAvailableFailsAfterSuccess)
184{
185 getToVerificationCompleted(VerifyCheckResponses::success);
186
187 auto blobs = handler->getBlobIds();
188 for (const auto& blob : blobs)
189 {
190 EXPECT_FALSE(handler->open(session + 1, flags, blob));
191 }
192}
193
194TEST_F(FirmwareHandlerVerificationCompletedTest,
195 OpeningAnyBlobAvailableFailsAfterFailure)
196{
197 getToVerificationCompleted(VerifyCheckResponses::failed);
198
199 auto blobs = handler->getBlobIds();
200 for (const auto& blob : blobs)
201 {
202 EXPECT_FALSE(handler->open(session + 1, flags, blob));
203 }
204}
Patrick Venturea82f99e2019-05-24 15:44:35 -0700205
206/*
207 * writemeta(session) - write meta should fail.
Patrick Venture4d9b0e12019-05-29 10:21:40 -0700208 */
Patrick Venture2b801372019-05-29 10:26:01 -0700209TEST_F(FirmwareHandlerVerificationCompletedTest,
210 WriteMetaToVerifyBlobReturnsFailure)
211{
212 getToVerificationCompleted(VerifyCheckResponses::success);
213
214 std::vector<std::uint8_t> bytes = {0x01, 0x02};
215 EXPECT_FALSE(handler->writeMeta(session, 0, bytes));
216}
Patrick Venture4d9b0e12019-05-29 10:21:40 -0700217
218/*
Patrick Venturea82f99e2019-05-24 15:44:35 -0700219 * write(session) - write should fail.
Patrick Venture65cdcf02019-05-29 10:18:50 -0700220 */
Patrick Venture4d9b0e12019-05-29 10:21:40 -0700221TEST_F(FirmwareHandlerVerificationCompletedTest,
222 WriteToVerifyBlobReturnsFailure)
223{
224 getToVerificationCompleted(VerifyCheckResponses::success);
225
226 std::vector<std::uint8_t> bytes = {0x01, 0x02};
227 EXPECT_FALSE(handler->write(session, 0, bytes));
228}
Patrick Venture65cdcf02019-05-29 10:18:50 -0700229
230/*
Patrick Venturea82f99e2019-05-24 15:44:35 -0700231 * read(session) - read returns empty.
Patrick Venture65cdcf02019-05-29 10:18:50 -0700232 */
233TEST_F(FirmwareHandlerVerificationCompletedTest, ReadOfVerifyBlobReturnsEmpty)
234{
235 getToVerificationCompleted(VerifyCheckResponses::success);
236 EXPECT_THAT(handler->read(session, 0, 1), IsEmpty());
237}
238
239/*
Patrick Venturea82f99e2019-05-24 15:44:35 -0700240 * commit(session) - ?
241 */
242
Patrick Venture65cdcf02019-05-29 10:18:50 -0700243/*
244 * close(session) - close on the verify blobid:
245 * 1. if successful adds update blob id, changes state to UpdatePending
246 * 2. if unsuccessful doesn't add update blob id, changes state to?
247 */
248
Patrick Venturea82f99e2019-05-24 15:44:35 -0700249} // namespace
250} // namespace ipmi_flash