diff options
author | Sage Weil <sage@newdream.net> | 2009-12-21 17:49:37 -0500 |
---|---|---|
committer | Sage Weil <sage@newdream.net> | 2009-12-21 19:39:59 -0500 |
commit | 30dc6381bbac213987be6fe0b0fb89868ff1f2c0 (patch) | |
tree | f647d1826a3f8cf07a510cad49c9f400359a9ae4 | |
parent | 5de7bf8afa87f75af5ef3d6f9fce3e171cac834c (diff) |
ceph: fix error paths for corrupt osdmap messages
Both osdmap_decode() and osdmap_apply_incremental() should never return
NULL.
Signed-off-by: Sage Weil <sage@newdream.net>
-rw-r--r-- | fs/ceph/osd_client.c | 2 | ||||
-rw-r--r-- | fs/ceph/osdmap.c | 11 |
2 files changed, 8 insertions, 5 deletions
diff --git a/fs/ceph/osd_client.c b/fs/ceph/osd_client.c index 4bfe880d53c8..b474b3ad61f0 100644 --- a/fs/ceph/osd_client.c +++ b/fs/ceph/osd_client.c | |||
@@ -910,6 +910,7 @@ void ceph_osdc_handle_map(struct ceph_osd_client *osdc, struct ceph_msg *msg) | |||
910 | err = PTR_ERR(newmap); | 910 | err = PTR_ERR(newmap); |
911 | goto bad; | 911 | goto bad; |
912 | } | 912 | } |
913 | BUG_ON(!newmap); | ||
913 | if (newmap != osdc->osdmap) { | 914 | if (newmap != osdc->osdmap) { |
914 | ceph_osdmap_destroy(osdc->osdmap); | 915 | ceph_osdmap_destroy(osdc->osdmap); |
915 | osdc->osdmap = newmap; | 916 | osdc->osdmap = newmap; |
@@ -946,6 +947,7 @@ void ceph_osdc_handle_map(struct ceph_osd_client *osdc, struct ceph_msg *msg) | |||
946 | err = PTR_ERR(newmap); | 947 | err = PTR_ERR(newmap); |
947 | goto bad; | 948 | goto bad; |
948 | } | 949 | } |
950 | BUG_ON(!newmap); | ||
949 | oldmap = osdc->osdmap; | 951 | oldmap = osdc->osdmap; |
950 | osdc->osdmap = newmap; | 952 | osdc->osdmap = newmap; |
951 | if (oldmap) | 953 | if (oldmap) |
diff --git a/fs/ceph/osdmap.c b/fs/ceph/osdmap.c index 8c8ffe5ef7d4..a9416308de6f 100644 --- a/fs/ceph/osdmap.c +++ b/fs/ceph/osdmap.c | |||
@@ -200,6 +200,7 @@ static struct crush_map *crush_decode(void *pbyval, void *end) | |||
200 | size = sizeof(struct crush_bucket_straw); | 200 | size = sizeof(struct crush_bucket_straw); |
201 | break; | 201 | break; |
202 | default: | 202 | default: |
203 | err = -EINVAL; | ||
203 | goto bad; | 204 | goto bad; |
204 | } | 205 | } |
205 | BUG_ON(size == 0); | 206 | BUG_ON(size == 0); |
@@ -278,6 +279,7 @@ static struct crush_map *crush_decode(void *pbyval, void *end) | |||
278 | /* len */ | 279 | /* len */ |
279 | ceph_decode_32_safe(p, end, yes, bad); | 280 | ceph_decode_32_safe(p, end, yes, bad); |
280 | #if BITS_PER_LONG == 32 | 281 | #if BITS_PER_LONG == 32 |
282 | err = -EINVAL; | ||
281 | if (yes > ULONG_MAX / sizeof(struct crush_rule_step)) | 283 | if (yes > ULONG_MAX / sizeof(struct crush_rule_step)) |
282 | goto bad; | 284 | goto bad; |
283 | #endif | 285 | #endif |
@@ -489,11 +491,10 @@ struct ceph_osdmap *osdmap_decode(void **p, void *end) | |||
489 | ceph_decode_copy(p, &pgid, sizeof(pgid)); | 491 | ceph_decode_copy(p, &pgid, sizeof(pgid)); |
490 | n = ceph_decode_32(p); | 492 | n = ceph_decode_32(p); |
491 | ceph_decode_need(p, end, n * sizeof(u32), bad); | 493 | ceph_decode_need(p, end, n * sizeof(u32), bad); |
494 | err = -ENOMEM; | ||
492 | pg = kmalloc(sizeof(*pg) + n*sizeof(u32), GFP_NOFS); | 495 | pg = kmalloc(sizeof(*pg) + n*sizeof(u32), GFP_NOFS); |
493 | if (!pg) { | 496 | if (!pg) |
494 | err = -ENOMEM; | ||
495 | goto bad; | 497 | goto bad; |
496 | } | ||
497 | pg->pgid = pgid; | 498 | pg->pgid = pgid; |
498 | pg->len = n; | 499 | pg->len = n; |
499 | for (j = 0; j < n; j++) | 500 | for (j = 0; j < n; j++) |
@@ -564,8 +565,7 @@ struct ceph_osdmap *osdmap_apply_incremental(void **p, void *end, | |||
564 | if (len > 0) { | 565 | if (len > 0) { |
565 | dout("apply_incremental full map len %d, %p to %p\n", | 566 | dout("apply_incremental full map len %d, %p to %p\n", |
566 | len, *p, end); | 567 | len, *p, end); |
567 | newmap = osdmap_decode(p, min(*p+len, end)); | 568 | return osdmap_decode(p, min(*p+len, end)); |
568 | return newmap; /* error or not */ | ||
569 | } | 569 | } |
570 | 570 | ||
571 | /* new crush? */ | 571 | /* new crush? */ |
@@ -809,6 +809,7 @@ int ceph_calc_object_layout(struct ceph_object_layout *ol, | |||
809 | struct ceph_pg_pool_info *pool; | 809 | struct ceph_pg_pool_info *pool; |
810 | unsigned ps; | 810 | unsigned ps; |
811 | 811 | ||
812 | BUG_ON(!osdmap); | ||
812 | if (poolid >= osdmap->num_pools) | 813 | if (poolid >= osdmap->num_pools) |
813 | return -EIO; | 814 | return -EIO; |
814 | 815 | ||