Commit 0ed7285e authored by Sage Weil's avatar Sage Weil Committed by Alex Elder

libceph: fix osdmap decode error paths

Ensure that we set the err value correctly so that we do not pass a 0
value to ERR_PTR and confuse the calling code.  (In particular,
osd_client.c handle_map() will BUG(!newmap)).
Signed-off-by: default avatarSage Weil <sage@inktank.com>
Reviewed-by: default avatarAlex Elder <elder@inktank.com>
parent 069a4b56
...@@ -645,10 +645,12 @@ struct ceph_osdmap *osdmap_decode(void **p, void *end) ...@@ -645,10 +645,12 @@ struct ceph_osdmap *osdmap_decode(void **p, void *end)
ceph_decode_32_safe(p, end, max, bad); ceph_decode_32_safe(p, end, max, bad);
while (max--) { while (max--) {
ceph_decode_need(p, end, 4 + 1 + sizeof(pi->v), bad); ceph_decode_need(p, end, 4 + 1 + sizeof(pi->v), bad);
err = -ENOMEM;
pi = kzalloc(sizeof(*pi), GFP_NOFS); pi = kzalloc(sizeof(*pi), GFP_NOFS);
if (!pi) if (!pi)
goto bad; goto bad;
pi->id = ceph_decode_32(p); pi->id = ceph_decode_32(p);
err = -EINVAL;
ev = ceph_decode_8(p); /* encoding version */ ev = ceph_decode_8(p); /* encoding version */
if (ev > CEPH_PG_POOL_VERSION) { if (ev > CEPH_PG_POOL_VERSION) {
pr_warning("got unknown v %d > %d of ceph_pg_pool\n", pr_warning("got unknown v %d > %d of ceph_pg_pool\n",
...@@ -664,8 +666,13 @@ struct ceph_osdmap *osdmap_decode(void **p, void *end) ...@@ -664,8 +666,13 @@ struct ceph_osdmap *osdmap_decode(void **p, void *end)
__insert_pg_pool(&map->pg_pools, pi); __insert_pg_pool(&map->pg_pools, pi);
} }
if (version >= 5 && __decode_pool_names(p, end, map) < 0) if (version >= 5) {
err = __decode_pool_names(p, end, map);
if (err < 0) {
dout("fail to decode pool names");
goto bad; goto bad;
}
}
ceph_decode_32_safe(p, end, map->pool_max, bad); ceph_decode_32_safe(p, end, map->pool_max, bad);
...@@ -745,7 +752,7 @@ struct ceph_osdmap *osdmap_decode(void **p, void *end) ...@@ -745,7 +752,7 @@ struct ceph_osdmap *osdmap_decode(void **p, void *end)
return map; return map;
bad: bad:
dout("osdmap_decode fail\n"); dout("osdmap_decode fail err %d\n", err);
ceph_osdmap_destroy(map); ceph_osdmap_destroy(map);
return ERR_PTR(err); return ERR_PTR(err);
} }
...@@ -839,6 +846,7 @@ struct ceph_osdmap *osdmap_apply_incremental(void **p, void *end, ...@@ -839,6 +846,7 @@ struct ceph_osdmap *osdmap_apply_incremental(void **p, void *end,
if (ev > CEPH_PG_POOL_VERSION) { if (ev > CEPH_PG_POOL_VERSION) {
pr_warning("got unknown v %d > %d of ceph_pg_pool\n", pr_warning("got unknown v %d > %d of ceph_pg_pool\n",
ev, CEPH_PG_POOL_VERSION); ev, CEPH_PG_POOL_VERSION);
err = -EINVAL;
goto bad; goto bad;
} }
pi = __lookup_pg_pool(&map->pg_pools, pool); pi = __lookup_pg_pool(&map->pg_pools, pool);
...@@ -855,8 +863,11 @@ struct ceph_osdmap *osdmap_apply_incremental(void **p, void *end, ...@@ -855,8 +863,11 @@ struct ceph_osdmap *osdmap_apply_incremental(void **p, void *end,
if (err < 0) if (err < 0)
goto bad; goto bad;
} }
if (version >= 5 && __decode_pool_names(p, end, map) < 0) if (version >= 5) {
err = __decode_pool_names(p, end, map);
if (err < 0)
goto bad; goto bad;
}
/* old_pool */ /* old_pool */
ceph_decode_32_safe(p, end, len, bad); ceph_decode_32_safe(p, end, len, bad);
...@@ -932,15 +943,13 @@ struct ceph_osdmap *osdmap_apply_incremental(void **p, void *end, ...@@ -932,15 +943,13 @@ struct ceph_osdmap *osdmap_apply_incremental(void **p, void *end,
(void) __remove_pg_mapping(&map->pg_temp, pgid); (void) __remove_pg_mapping(&map->pg_temp, pgid);
/* insert */ /* insert */
if (pglen > (UINT_MAX - sizeof(*pg)) / sizeof(u32)) {
err = -EINVAL; err = -EINVAL;
if (pglen > (UINT_MAX - sizeof(*pg)) / sizeof(u32))
goto bad; goto bad;
}
pg = kmalloc(sizeof(*pg) + sizeof(u32)*pglen, GFP_NOFS);
if (!pg) {
err = -ENOMEM; err = -ENOMEM;
pg = kmalloc(sizeof(*pg) + sizeof(u32)*pglen, GFP_NOFS);
if (!pg)
goto bad; goto bad;
}
pg->pgid = pgid; pg->pgid = pgid;
pg->len = pglen; pg->len = pglen;
for (j = 0; j < pglen; j++) for (j = 0; j < pglen; j++)
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment