]> git.proxmox.com Git - ceph.git/blob - ceph/src/test/librbd/object_map/test_mock_ResizeRequest.cc
import 15.2.0 Octopus source
[ceph.git] / ceph / src / test / librbd / object_map / test_mock_ResizeRequest.cc
1 // -*- mode:C++; tab-width:8; c-basic-offset:2; indent-tabs-mode:t -*-
2 // vim: ts=8 sw=2 smarttab
3
4 #include "test/librbd/test_mock_fixture.h"
5 #include "test/librbd/test_support.h"
6 #include "test/librados_test_stub/MockTestMemIoCtxImpl.h"
7 #include "common/bit_vector.hpp"
8 #include "librbd/internal.h"
9 #include "librbd/ObjectMap.h"
10 #include "librbd/api/Image.h"
11 #include "librbd/object_map/ResizeRequest.h"
12 #include "gmock/gmock.h"
13 #include "gtest/gtest.h"
14
15 namespace librbd {
16 namespace object_map {
17
18 using ::testing::_;
19 using ::testing::DoDefault;
20 using ::testing::Return;
21 using ::testing::StrEq;
22
23 class TestMockObjectMapResizeRequest : public TestMockFixture {
24 public:
25 void expect_resize(librbd::ImageCtx *ictx, uint64_t snap_id, int r) {
26 std::string oid(ObjectMap<>::object_map_name(ictx->id, snap_id));
27 if (snap_id == CEPH_NOSNAP) {
28 EXPECT_CALL(get_mock_io_ctx(ictx->md_ctx),
29 exec(oid, _, StrEq("lock"), StrEq("assert_locked"), _, _, _))
30 .WillOnce(DoDefault());
31 }
32
33 if (r < 0) {
34 EXPECT_CALL(get_mock_io_ctx(ictx->md_ctx),
35 exec(oid, _, StrEq("rbd"), StrEq("object_map_resize"), _, _, _))
36 .WillOnce(Return(r));
37 } else {
38 EXPECT_CALL(get_mock_io_ctx(ictx->md_ctx),
39 exec(oid, _, StrEq("rbd"), StrEq("object_map_resize"), _, _, _))
40 .WillOnce(DoDefault());
41 }
42 }
43
44 void expect_invalidate(librbd::ImageCtx *ictx) {
45 EXPECT_CALL(get_mock_io_ctx(ictx->md_ctx),
46 exec(ictx->header_oid, _, StrEq("rbd"), StrEq("set_flags"), _, _, _))
47 .WillOnce(DoDefault());
48 }
49 };
50
51 TEST_F(TestMockObjectMapResizeRequest, UpdateInMemory) {
52 REQUIRE_FEATURE(RBD_FEATURE_OBJECT_MAP);
53
54 librbd::ImageCtx *ictx;
55 ASSERT_EQ(0, open_image(m_image_name, &ictx));
56 ASSERT_EQ(0, acquire_exclusive_lock(*ictx));
57
58 ceph::shared_mutex object_map_lock = ceph::make_shared_mutex("lock");
59 ceph::BitVector<2> object_map;
60 object_map.resize(1);
61
62 C_SaferCond cond_ctx;
63 AsyncRequest<> *req = new ResizeRequest(
64 *ictx, &object_map_lock, &object_map, CEPH_NOSNAP, object_map.size(),
65 OBJECT_EXISTS, &cond_ctx);
66 req->send();
67 ASSERT_EQ(0, cond_ctx.wait());
68
69 for (uint64_t i = 0; i < object_map.size(); ++i) {
70 ASSERT_EQ(i == 0 ? OBJECT_NONEXISTENT : OBJECT_EXISTS,
71 object_map[i]);
72 }
73 }
74
75 TEST_F(TestMockObjectMapResizeRequest, UpdateHeadOnDisk) {
76 REQUIRE_FEATURE(RBD_FEATURE_OBJECT_MAP);
77
78 librbd::ImageCtx *ictx;
79 ASSERT_EQ(0, open_image(m_image_name, &ictx));
80 ASSERT_EQ(0, acquire_exclusive_lock(*ictx));
81
82 expect_resize(ictx, CEPH_NOSNAP, 0);
83
84 ceph::shared_mutex object_map_lock = ceph::make_shared_mutex("lock");
85 ceph::BitVector<2> object_map;
86 object_map.resize(1);
87
88 C_SaferCond cond_ctx;
89 AsyncRequest<> *req = new ResizeRequest(
90 *ictx, &object_map_lock, &object_map, CEPH_NOSNAP, object_map.size(),
91 OBJECT_EXISTS, &cond_ctx);
92 req->send();
93 ASSERT_EQ(0, cond_ctx.wait());
94
95 expect_unlock_exclusive_lock(*ictx);
96 }
97
98 TEST_F(TestMockObjectMapResizeRequest, UpdateSnapOnDisk) {
99 REQUIRE_FEATURE(RBD_FEATURE_OBJECT_MAP);
100
101 librbd::ImageCtx *ictx;
102 ASSERT_EQ(0, open_image(m_image_name, &ictx));
103 ASSERT_EQ(0, snap_create(*ictx, "snap1"));
104 ASSERT_EQ(0, librbd::api::Image<>::snap_set(ictx,
105 cls::rbd::UserSnapshotNamespace(),
106 "snap1"));
107
108 uint64_t snap_id = ictx->snap_id;
109 expect_resize(ictx, snap_id, 0);
110
111 ceph::shared_mutex object_map_lock = ceph::make_shared_mutex("lock");
112 ceph::BitVector<2> object_map;
113 object_map.resize(1);
114
115 C_SaferCond cond_ctx;
116 AsyncRequest<> *req = new ResizeRequest(
117 *ictx, &object_map_lock, &object_map, snap_id, object_map.size(),
118 OBJECT_EXISTS, &cond_ctx);
119 req->send();
120 ASSERT_EQ(0, cond_ctx.wait());
121
122 expect_unlock_exclusive_lock(*ictx);
123 }
124
125 TEST_F(TestMockObjectMapResizeRequest, UpdateOnDiskError) {
126 REQUIRE_FEATURE(RBD_FEATURE_OBJECT_MAP);
127
128 librbd::ImageCtx *ictx;
129 ASSERT_EQ(0, open_image(m_image_name, &ictx));
130 ASSERT_EQ(0, acquire_exclusive_lock(*ictx));
131
132 expect_resize(ictx, CEPH_NOSNAP, -EINVAL);
133 expect_invalidate(ictx);
134
135 ceph::shared_mutex object_map_lock = ceph::make_shared_mutex("lock");
136 ceph::BitVector<2> object_map;
137 object_map.resize(1);
138
139 C_SaferCond cond_ctx;
140 AsyncRequest<> *req = new ResizeRequest(
141 *ictx, &object_map_lock, &object_map, CEPH_NOSNAP, object_map.size(),
142 OBJECT_EXISTS, &cond_ctx);
143 req->send();
144 ASSERT_EQ(0, cond_ctx.wait());
145
146 expect_unlock_exclusive_lock(*ictx);
147 }
148
149 } // namespace object_map
150 } // namespace librbd