]> git.ipfire.org Git - thirdparty/kernel/stable.git/commitdiff
libceph, rbd: ignore addr->type while comparing in some cases
authorIlya Dryomov <idryomov@gmail.com>
Wed, 25 Nov 2020 13:41:59 +0000 (14:41 +0100)
committerGreg Kroah-Hartman <gregkh@linuxfoundation.org>
Wed, 30 Aug 2023 14:23:11 +0000 (16:23 +0200)
[ Upstream commit 313771e80fd253d4b5472e61a2d12b03c5293aa9 ]

For libceph, this ensures that libceph instance sharing (share option)
continues to work.  For rbd, this avoids blocklisting alive lock owners
(locker addr is always LEGACY, while watcher addr is ANY in nautilus).

Signed-off-by: Ilya Dryomov <idryomov@gmail.com>
Stable-dep-of: 588159009d5b ("rbd: retrieve and check lock owner twice before blocklisting")
Signed-off-by: Sasha Levin <sashal@kernel.org>
drivers/block/rbd.c
include/linux/ceph/msgr.h
net/ceph/mon_client.c

index 63491748dc8d7d4b11504b3259bab6e0e0e44eaa..7b8731cddd9eab99156b1a30f61603dc899b6304 100644 (file)
@@ -3979,8 +3979,12 @@ static int find_watcher(struct rbd_device *rbd_dev,
 
        sscanf(locker->id.cookie, RBD_LOCK_COOKIE_PREFIX " %llu", &cookie);
        for (i = 0; i < num_watchers; i++) {
-               if (!memcmp(&watchers[i].addr, &locker->info.addr,
-                           sizeof(locker->info.addr)) &&
+               /*
+                * Ignore addr->type while comparing.  This mimics
+                * entity_addr_t::get_legacy_str() + strcmp().
+                */
+               if (ceph_addr_equal_no_type(&watchers[i].addr,
+                                           &locker->info.addr) &&
                    watchers[i].cookie == cookie) {
                        struct rbd_client_id cid = {
                                .gid = le64_to_cpu(watchers[i].name.num),
index 9e50aede46c8327bec9309b2ad21eb1ecff2c711..7bde0af29a8148f878cae93d90af648fe62a3a81 100644 (file)
@@ -61,11 +61,18 @@ extern const char *ceph_entity_type_name(int type);
  * entity_addr -- network address
  */
 struct ceph_entity_addr {
-       __le32 type;
+       __le32 type;  /* CEPH_ENTITY_ADDR_TYPE_* */
        __le32 nonce;  /* unique id for process (e.g. pid) */
        struct sockaddr_storage in_addr;
 } __attribute__ ((packed));
 
+static inline bool ceph_addr_equal_no_type(const struct ceph_entity_addr *lhs,
+                                          const struct ceph_entity_addr *rhs)
+{
+       return !memcmp(&lhs->in_addr, &rhs->in_addr, sizeof(lhs->in_addr)) &&
+              lhs->nonce == rhs->nonce;
+}
+
 struct ceph_entity_inst {
        struct ceph_entity_name name;
        struct ceph_entity_addr addr;
index c4cf2529d08ba9d76e8a55df411eafc9d3e67ae4..ef5c174102d5e3114e54d31c8c76d43c42d77978 100644 (file)
@@ -96,9 +96,11 @@ int ceph_monmap_contains(struct ceph_monmap *m, struct ceph_entity_addr *addr)
 {
        int i;
 
-       for (i = 0; i < m->num_mon; i++)
-               if (memcmp(addr, &m->mon_inst[i].addr, sizeof(*addr)) == 0)
+       for (i = 0; i < m->num_mon; i++) {
+               if (ceph_addr_equal_no_type(addr, &m->mon_inst[i].addr))
                        return 1;
+       }
+
        return 0;
 }