aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--fs/ceph/osdmap.c180
-rw-r--r--fs/ceph/osdmap.h1
-rw-r--r--fs/ceph/rados.h6
3 files changed, 114 insertions, 73 deletions
diff --git a/fs/ceph/osdmap.c b/fs/ceph/osdmap.c
index d82fe87c2a6e..7526d6d33016 100644
--- a/fs/ceph/osdmap.c
+++ b/fs/ceph/osdmap.c
@@ -312,71 +312,6 @@ bad:
312 return ERR_PTR(err); 312 return ERR_PTR(err);
313} 313}
314 314
315
316/*
317 * osd map
318 */
319void ceph_osdmap_destroy(struct ceph_osdmap *map)
320{
321 dout("osdmap_destroy %p\n", map);
322 if (map->crush)
323 crush_destroy(map->crush);
324 while (!RB_EMPTY_ROOT(&map->pg_temp)) {
325 struct ceph_pg_mapping *pg =
326 rb_entry(rb_first(&map->pg_temp),
327 struct ceph_pg_mapping, node);
328 rb_erase(&pg->node, &map->pg_temp);
329 kfree(pg);
330 }
331 while (!RB_EMPTY_ROOT(&map->pg_pools)) {
332 struct ceph_pg_pool_info *pi =
333 rb_entry(rb_first(&map->pg_pools),
334 struct ceph_pg_pool_info, node);
335 rb_erase(&pi->node, &map->pg_pools);
336 kfree(pi);
337 }
338 kfree(map->osd_state);
339 kfree(map->osd_weight);
340 kfree(map->osd_addr);
341 kfree(map);
342}
343
344/*
345 * adjust max osd value. reallocate arrays.
346 */
347static int osdmap_set_max_osd(struct ceph_osdmap *map, int max)
348{
349 u8 *state;
350 struct ceph_entity_addr *addr;
351 u32 *weight;
352
353 state = kcalloc(max, sizeof(*state), GFP_NOFS);
354 addr = kcalloc(max, sizeof(*addr), GFP_NOFS);
355 weight = kcalloc(max, sizeof(*weight), GFP_NOFS);
356 if (state == NULL || addr == NULL || weight == NULL) {
357 kfree(state);
358 kfree(addr);
359 kfree(weight);
360 return -ENOMEM;
361 }
362
363 /* copy old? */
364 if (map->osd_state) {
365 memcpy(state, map->osd_state, map->max_osd*sizeof(*state));
366 memcpy(addr, map->osd_addr, map->max_osd*sizeof(*addr));
367 memcpy(weight, map->osd_weight, map->max_osd*sizeof(*weight));
368 kfree(map->osd_state);
369 kfree(map->osd_addr);
370 kfree(map->osd_weight);
371 }
372
373 map->osd_state = state;
374 map->osd_weight = weight;
375 map->osd_addr = addr;
376 map->max_osd = max;
377 return 0;
378}
379
380/* 315/*
381 * rbtree of pg_mapping for handling pg_temp (explicit mapping of pgid 316 * rbtree of pg_mapping for handling pg_temp (explicit mapping of pgid
382 * to a set of osds) 317 * to a set of osds)
@@ -480,6 +415,13 @@ static struct ceph_pg_pool_info *__lookup_pg_pool(struct rb_root *root, int id)
480 return NULL; 415 return NULL;
481} 416}
482 417
418static void __remove_pg_pool(struct rb_root *root, struct ceph_pg_pool_info *pi)
419{
420 rb_erase(&pi->node, root);
421 kfree(pi->name);
422 kfree(pi);
423}
424
483void __decode_pool(void **p, struct ceph_pg_pool_info *pi) 425void __decode_pool(void **p, struct ceph_pg_pool_info *pi)
484{ 426{
485 ceph_decode_copy(p, &pi->v, sizeof(pi->v)); 427 ceph_decode_copy(p, &pi->v, sizeof(pi->v));
@@ -488,6 +430,98 @@ void __decode_pool(void **p, struct ceph_pg_pool_info *pi)
488 *p += le32_to_cpu(pi->v.num_removed_snap_intervals) * sizeof(u64) * 2; 430 *p += le32_to_cpu(pi->v.num_removed_snap_intervals) * sizeof(u64) * 2;
489} 431}
490 432
433static int __decode_pool_names(void **p, void *end, struct ceph_osdmap *map)
434{
435 struct ceph_pg_pool_info *pi;
436 u32 num, len, pool;
437
438 ceph_decode_32_safe(p, end, num, bad);
439 dout(" %d pool names\n", num);
440 while (num--) {
441 ceph_decode_32_safe(p, end, pool, bad);
442 ceph_decode_32_safe(p, end, len, bad);
443 dout(" pool %d len %d\n", pool, len);
444 pi = __lookup_pg_pool(&map->pg_pools, pool);
445 if (pi) {
446 kfree(pi->name);
447 pi->name = kmalloc(len + 1, GFP_NOFS);
448 if (pi->name) {
449 memcpy(pi->name, *p, len);
450 pi->name[len] = '\0';
451 dout(" name is %s\n", pi->name);
452 }
453 }
454 *p += len;
455 }
456 return 0;
457
458bad:
459 return -EINVAL;
460}
461
462/*
463 * osd map
464 */
465void ceph_osdmap_destroy(struct ceph_osdmap *map)
466{
467 dout("osdmap_destroy %p\n", map);
468 if (map->crush)
469 crush_destroy(map->crush);
470 while (!RB_EMPTY_ROOT(&map->pg_temp)) {
471 struct ceph_pg_mapping *pg =
472 rb_entry(rb_first(&map->pg_temp),
473 struct ceph_pg_mapping, node);
474 rb_erase(&pg->node, &map->pg_temp);
475 kfree(pg);
476 }
477 while (!RB_EMPTY_ROOT(&map->pg_pools)) {
478 struct ceph_pg_pool_info *pi =
479 rb_entry(rb_first(&map->pg_pools),
480 struct ceph_pg_pool_info, node);
481 __remove_pg_pool(&map->pg_pools, pi);
482 }
483 kfree(map->osd_state);
484 kfree(map->osd_weight);
485 kfree(map->osd_addr);
486 kfree(map);
487}
488
489/*
490 * adjust max osd value. reallocate arrays.
491 */
492static int osdmap_set_max_osd(struct ceph_osdmap *map, int max)
493{
494 u8 *state;
495 struct ceph_entity_addr *addr;
496 u32 *weight;
497
498 state = kcalloc(max, sizeof(*state), GFP_NOFS);
499 addr = kcalloc(max, sizeof(*addr), GFP_NOFS);
500 weight = kcalloc(max, sizeof(*weight), GFP_NOFS);
501 if (state == NULL || addr == NULL || weight == NULL) {
502 kfree(state);
503 kfree(addr);
504 kfree(weight);
505 return -ENOMEM;
506 }
507
508 /* copy old? */
509 if (map->osd_state) {
510 memcpy(state, map->osd_state, map->max_osd*sizeof(*state));
511 memcpy(addr, map->osd_addr, map->max_osd*sizeof(*addr));
512 memcpy(weight, map->osd_weight, map->max_osd*sizeof(*weight));
513 kfree(map->osd_state);
514 kfree(map->osd_addr);
515 kfree(map->osd_weight);
516 }
517
518 map->osd_state = state;
519 map->osd_weight = weight;
520 map->osd_addr = addr;
521 map->max_osd = max;
522 return 0;
523}
524
491/* 525/*
492 * decode a full map. 526 * decode a full map.
493 */ 527 */
@@ -524,7 +558,7 @@ struct ceph_osdmap *osdmap_decode(void **p, void *end)
524 ceph_decode_32_safe(p, end, max, bad); 558 ceph_decode_32_safe(p, end, max, bad);
525 while (max--) { 559 while (max--) {
526 ceph_decode_need(p, end, 4 + 1 + sizeof(pi->v), bad); 560 ceph_decode_need(p, end, 4 + 1 + sizeof(pi->v), bad);
527 pi = kmalloc(sizeof(*pi), GFP_NOFS); 561 pi = kzalloc(sizeof(*pi), GFP_NOFS);
528 if (!pi) 562 if (!pi)
529 goto bad; 563 goto bad;
530 pi->id = ceph_decode_32(p); 564 pi->id = ceph_decode_32(p);
@@ -537,6 +571,10 @@ struct ceph_osdmap *osdmap_decode(void **p, void *end)
537 __decode_pool(p, pi); 571 __decode_pool(p, pi);
538 __insert_pg_pool(&map->pg_pools, pi); 572 __insert_pg_pool(&map->pg_pools, pi);
539 } 573 }
574
575 if (version >= 5 && __decode_pool_names(p, end, map) < 0)
576 goto bad;
577
540 ceph_decode_32_safe(p, end, map->pool_max, bad); 578 ceph_decode_32_safe(p, end, map->pool_max, bad);
541 579
542 ceph_decode_32_safe(p, end, map->flags, bad); 580 ceph_decode_32_safe(p, end, map->flags, bad);
@@ -710,7 +748,7 @@ struct ceph_osdmap *osdmap_apply_incremental(void **p, void *end,
710 } 748 }
711 pi = __lookup_pg_pool(&map->pg_pools, pool); 749 pi = __lookup_pg_pool(&map->pg_pools, pool);
712 if (!pi) { 750 if (!pi) {
713 pi = kmalloc(sizeof(*pi), GFP_NOFS); 751 pi = kzalloc(sizeof(*pi), GFP_NOFS);
714 if (!pi) { 752 if (!pi) {
715 err = -ENOMEM; 753 err = -ENOMEM;
716 goto bad; 754 goto bad;
@@ -720,6 +758,8 @@ struct ceph_osdmap *osdmap_apply_incremental(void **p, void *end,
720 } 758 }
721 __decode_pool(p, pi); 759 __decode_pool(p, pi);
722 } 760 }
761 if (version >= 5 && __decode_pool_names(p, end, map) < 0)
762 goto bad;
723 763
724 /* old_pool */ 764 /* old_pool */
725 ceph_decode_32_safe(p, end, len, bad); 765 ceph_decode_32_safe(p, end, len, bad);
@@ -728,10 +768,8 @@ struct ceph_osdmap *osdmap_apply_incremental(void **p, void *end,
728 768
729 ceph_decode_32_safe(p, end, pool, bad); 769 ceph_decode_32_safe(p, end, pool, bad);
730 pi = __lookup_pg_pool(&map->pg_pools, pool); 770 pi = __lookup_pg_pool(&map->pg_pools, pool);
731 if (pi) { 771 if (pi)
732 rb_erase(&pi->node, &map->pg_pools); 772 __remove_pg_pool(&map->pg_pools, pi);
733 kfree(pi);
734 }
735 } 773 }
736 774
737 /* new_up */ 775 /* new_up */
diff --git a/fs/ceph/osdmap.h b/fs/ceph/osdmap.h
index 1fb55afb2642..8bc9f1e4f562 100644
--- a/fs/ceph/osdmap.h
+++ b/fs/ceph/osdmap.h
@@ -23,6 +23,7 @@ struct ceph_pg_pool_info {
23 int id; 23 int id;
24 struct ceph_pg_pool v; 24 struct ceph_pg_pool v;
25 int pg_num_mask, pgp_num_mask, lpg_num_mask, lpgp_num_mask; 25 int pg_num_mask, pgp_num_mask, lpg_num_mask, lpgp_num_mask;
26 char *name;
26}; 27};
27 28
28struct ceph_pg_mapping { 29struct ceph_pg_mapping {
diff --git a/fs/ceph/rados.h b/fs/ceph/rados.h
index 26ac8b89a676..a1fc1d017b58 100644
--- a/fs/ceph/rados.h
+++ b/fs/ceph/rados.h
@@ -11,8 +11,10 @@
11/* 11/*
12 * osdmap encoding versions 12 * osdmap encoding versions
13 */ 13 */
14#define CEPH_OSDMAP_INC_VERSION 4 14#define CEPH_OSDMAP_INC_VERSION 5
15#define CEPH_OSDMAP_VERSION 4 15#define CEPH_OSDMAP_INC_VERSION_EXT 5
16#define CEPH_OSDMAP_VERSION 5
17#define CEPH_OSDMAP_VERSION_EXT 5
16 18
17/* 19/*
18 * fs id 20 * fs id