]> git.proxmox.com Git - ceph.git/blob - ceph/src/test/librbd/test_ObjectMap.cc
update sources to 12.2.10
[ceph.git] / ceph / src / test / librbd / test_ObjectMap.cc
1 // -*- mode:C++; tab-width:8; c-basic-offset:2; indent-tabs-mode:t -*-
2 // vim: ts=8 sw=2 smarttab
3 #include "test/librbd/test_fixture.h"
4 #include "test/librbd/test_support.h"
5 #include "librbd/ExclusiveLock.h"
6 #include "librbd/ImageCtx.h"
7 #include "librbd/ImageState.h"
8 #include "librbd/ImageWatcher.h"
9 #include "librbd/internal.h"
10 #include "librbd/ObjectMap.h"
11 #include "cls/rbd/cls_rbd_client.h"
12 #include <list>
13
14 void register_test_object_map() {
15 }
16
17 class TestObjectMap : public TestFixture {
18 public:
19
20 int when_open_object_map(librbd::ImageCtx *ictx) {
21 C_SaferCond ctx;
22 librbd::ObjectMap<> object_map(*ictx, ictx->snap_id);
23 object_map.open(&ctx);
24 return ctx.wait();
25 }
26 };
27
28 TEST_F(TestObjectMap, RefreshInvalidatesWhenCorrupt) {
29 REQUIRE_FEATURE(RBD_FEATURE_OBJECT_MAP);
30
31 librbd::ImageCtx *ictx;
32 ASSERT_EQ(0, open_image(m_image_name, &ictx));
33 bool flags_set;
34 ASSERT_EQ(0, ictx->test_flags(CEPH_NOSNAP, RBD_FLAG_OBJECT_MAP_INVALID,
35 &flags_set));
36 ASSERT_FALSE(flags_set);
37
38 C_SaferCond lock_ctx;
39 {
40 RWLock::WLocker owner_locker(ictx->owner_lock);
41 ictx->exclusive_lock->try_acquire_lock(&lock_ctx);
42 }
43 ASSERT_EQ(0, lock_ctx.wait());
44
45 std::string oid = librbd::ObjectMap<>::object_map_name(ictx->id, CEPH_NOSNAP);
46 bufferlist bl;
47 bl.append("corrupt");
48 ASSERT_EQ(0, ictx->md_ctx.write_full(oid, bl));
49
50 ASSERT_EQ(0, when_open_object_map(ictx));
51 ASSERT_EQ(0, ictx->test_flags(CEPH_NOSNAP, RBD_FLAG_OBJECT_MAP_INVALID,
52 &flags_set));
53 ASSERT_TRUE(flags_set);
54 }
55
56 TEST_F(TestObjectMap, RefreshInvalidatesWhenTooSmall) {
57 REQUIRE_FEATURE(RBD_FEATURE_OBJECT_MAP);
58
59 librbd::ImageCtx *ictx;
60 ASSERT_EQ(0, open_image(m_image_name, &ictx));
61 bool flags_set;
62 ASSERT_EQ(0, ictx->test_flags(CEPH_NOSNAP, RBD_FLAG_OBJECT_MAP_INVALID,
63 &flags_set));
64 ASSERT_FALSE(flags_set);
65
66 C_SaferCond lock_ctx;
67 {
68 RWLock::WLocker owner_locker(ictx->owner_lock);
69 ictx->exclusive_lock->try_acquire_lock(&lock_ctx);
70 }
71 ASSERT_EQ(0, lock_ctx.wait());
72
73 librados::ObjectWriteOperation op;
74 librbd::cls_client::object_map_resize(&op, 0, OBJECT_NONEXISTENT);
75
76 std::string oid = librbd::ObjectMap<>::object_map_name(ictx->id, CEPH_NOSNAP);
77 ASSERT_EQ(0, ictx->md_ctx.operate(oid, &op));
78
79 ASSERT_EQ(0, when_open_object_map(ictx));
80 ASSERT_EQ(0, ictx->test_flags(CEPH_NOSNAP, RBD_FLAG_OBJECT_MAP_INVALID,
81 &flags_set));
82 ASSERT_TRUE(flags_set);
83 }
84
85 TEST_F(TestObjectMap, InvalidateFlagOnDisk) {
86 REQUIRE_FEATURE(RBD_FEATURE_OBJECT_MAP);
87
88 librbd::ImageCtx *ictx;
89 ASSERT_EQ(0, open_image(m_image_name, &ictx));
90 bool flags_set;
91 ASSERT_EQ(0, ictx->test_flags(CEPH_NOSNAP, RBD_FLAG_OBJECT_MAP_INVALID,
92 &flags_set));
93 ASSERT_FALSE(flags_set);
94
95 C_SaferCond lock_ctx;
96 {
97 RWLock::WLocker owner_locker(ictx->owner_lock);
98 ictx->exclusive_lock->try_acquire_lock(&lock_ctx);
99 }
100 ASSERT_EQ(0, lock_ctx.wait());
101
102 std::string oid = librbd::ObjectMap<>::object_map_name(ictx->id, CEPH_NOSNAP);
103 bufferlist bl;
104 bl.append("corrupt");
105 ASSERT_EQ(0, ictx->md_ctx.write_full(oid, bl));
106
107 ASSERT_EQ(0, when_open_object_map(ictx));
108 ASSERT_EQ(0, ictx->test_flags(CEPH_NOSNAP, RBD_FLAG_OBJECT_MAP_INVALID,
109 &flags_set));
110 ASSERT_TRUE(flags_set);
111
112 ASSERT_EQ(0, open_image(m_image_name, &ictx));
113 ASSERT_EQ(0, ictx->test_flags(CEPH_NOSNAP, RBD_FLAG_OBJECT_MAP_INVALID,
114 &flags_set));
115 ASSERT_TRUE(flags_set);
116 }
117
118 TEST_F(TestObjectMap, AcquireLockInvalidatesWhenTooSmall) {
119 REQUIRE_FEATURE(RBD_FEATURE_OBJECT_MAP);
120
121 librbd::ImageCtx *ictx;
122 ASSERT_EQ(0, open_image(m_image_name, &ictx));
123 bool flags_set;
124 ASSERT_EQ(0, ictx->test_flags(CEPH_NOSNAP, RBD_FLAG_OBJECT_MAP_INVALID,
125 &flags_set));
126 ASSERT_FALSE(flags_set);
127
128 librados::ObjectWriteOperation op;
129 librbd::cls_client::object_map_resize(&op, 0, OBJECT_NONEXISTENT);
130
131 std::string oid = librbd::ObjectMap<>::object_map_name(ictx->id, CEPH_NOSNAP);
132 ASSERT_EQ(0, ictx->md_ctx.operate(oid, &op));
133
134 C_SaferCond lock_ctx;
135 {
136 RWLock::WLocker owner_locker(ictx->owner_lock);
137 ictx->exclusive_lock->try_acquire_lock(&lock_ctx);
138 }
139 ASSERT_EQ(0, lock_ctx.wait());
140
141 ASSERT_EQ(0, ictx->test_flags(CEPH_NOSNAP, RBD_FLAG_OBJECT_MAP_INVALID,
142 &flags_set));
143 ASSERT_TRUE(flags_set);
144
145 // Test the flag is stored on disk
146 ASSERT_EQ(0, ictx->state->refresh());
147 ASSERT_EQ(0, ictx->test_flags(CEPH_NOSNAP, RBD_FLAG_OBJECT_MAP_INVALID,
148 &flags_set));
149 ASSERT_TRUE(flags_set);
150 }