From e2f41b2c6a8f97df211add545ed25b9e2bbb302b Mon Sep 17 00:00:00 2001 From: Adam Kwolek Date: Wed, 8 Jun 2011 16:46:37 +1000 Subject: [PATCH] imsm: check migration compatibility Under Windows IMSM can reshape arrays in 2 directions (ascending and decsending). Under Linux one (ascending) direction is supported at this moment. Block loading metadata when decsending reshape is detected Windows also uses optimalization area during reshaping array. Linux does not support it. The patch blocks this operation also. Signed-off-by: Maciej Trela Signed-off-by: Adam Kwolek Signed-off-by: Krzysztof Wojcik Signed-off-by: NeilBrown --- super-intel.c | 61 +++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 61 insertions(+) diff --git a/super-intel.c b/super-intel.c index 1ad7975..3d085c1 100644 --- a/super-intel.c +++ b/super-intel.c @@ -2840,6 +2840,44 @@ struct bbm_log *__get_imsm_bbm_log(struct imsm_super *mpb) return ptr; } +/******************************************************************************* + * Function: check_mpb_migr_compatibility + * Description: Function checks for unsupported migration features: + * - migration optimization area (pba_of_lba0) + * - descending reshape (ascending_migr) + * Parameters: + * super : imsm metadata information + * Returns: + * 0 : migration is compatible + * -1 : migration is not compatible + ******************************************************************************/ +int check_mpb_migr_compatibility(struct intel_super *super) +{ + struct imsm_map *map0, *map1; + struct migr_record *migr_rec = super->migr_rec; + int i; + + for (i = 0; i < super->anchor->num_raid_devs; i++) { + struct imsm_dev *dev_iter = __get_imsm_dev(super->anchor, i); + + if (dev_iter && + dev_iter->vol.migr_state == 1 && + dev_iter->vol.migr_type == MIGR_GEN_MIGR) { + /* This device is migrating */ + map0 = get_imsm_map(dev_iter, 0); + map1 = get_imsm_map(dev_iter, 1); + if (map0->pba_of_lba0 != map1->pba_of_lba0) + /* migration optimization area was used */ + return -1; + if (migr_rec->ascending_migr == 0 + && migr_rec->dest_depth_per_unit > 0) + /* descending reshape not supported yet */ + return -1; + } + } + return 0; +} + static void __free_imsm(struct intel_super *super, int free_disks); /* load_imsm_mpb - read matrix metadata @@ -3569,6 +3607,19 @@ static int load_super_imsm_all(struct supertype *st, int fd, void **sbp, err = 4; goto error; } + + /* Check migration compatibility */ + if (check_mpb_migr_compatibility(super) != 0) { + fprintf(stderr, Name ": Unsupported migration detected"); + if (devname) + fprintf(stderr, " on %s\n", devname); + else + fprintf(stderr, " (IMSM).\n"); + + err = 5; + goto error; + } + err = 0; error: @@ -3651,6 +3702,16 @@ static int load_super_imsm(struct supertype *st, int fd, char *devname) /* load migration record */ load_imsm_migr_rec(super, NULL); + /* Check for unsupported migration features */ + if (check_mpb_migr_compatibility(super) != 0) { + fprintf(stderr, Name ": Unsupported migration detected"); + if (devname) + fprintf(stderr, " on %s\n", devname); + else + fprintf(stderr, " (IMSM).\n"); + return 3; + } + return 0; }