Re: [PATCH] Implement compare function for dm-tables.

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



On Wed, Feb 18, 2009 at 07:32:17PM +0100, Hans de Goede wrote:
>
>
> Joel Granados Moreno wrote:
>> From: Joel Granados <joel.granados@xxxxxxxxx>
>>
>> modified:   device.py: We need to compare table from dmraid and from
>> device-mapper in a more general way.  It is possible to have an optional
>> argument in the table.  So its better not to hardcode the possition of
>> the devices in the table string.
>> ---
>>  device.py |   81 ++++++++++++++++++++++++++++++++++++++++++++----------------
>>  1 files changed, 59 insertions(+), 22 deletions(-)
>>
>> diff --git a/device.py b/device.py
>> index cbf196c..16c6b49 100644
>> --- a/device.py
>> +++ b/device.py
>> @@ -658,46 +658,83 @@ class RaidSet:
>>              pass
>>      bdev = property(get_bdev, None, None, "block.BlockDev")
>>  -    def get_map(self):
>> -        if not self._RaidSet__map is None:
>> -            return self._RaidSet__map
>> +    # Helper function for get_map
>> +    # The tables will be considered the same if, everything else being the
>> +    # same, they contain the same sets of devices.
>>  -        # we get "/dev/hda" from one and "3:0" from the other, so we 
>> have to
>> -        # fix up the device name
>> +    def equal(self, table1,  table2):
>>          def map_dev(path):
>>              if path[0] != '/':
>> -                return path.strip()
>> +                return path
>>               try:
>>                  statinfo = _os.stat(path)
>>                  if not _stat.S_ISBLK(statinfo.st_mode):
>> -                    return path.strip()
>> +                    return path
>>                   return "%d:%d" % (statinfo.st_rdev/256, 
>> statinfo.st_rdev%256, )
>>              except:
>> -                return path.strip()
>> +                return path
>>  -        parts = str(self.rs.dmTable).split(' ')
>> +        table1 = table1.strip().split(' ')
>> +        table2 = table2.strip().split(' ')
>> +        table1sets = []
>> +        table2sets = []
>>  -        table = []
>> -        for part in parts:
>> -            table += [map_dev(part),]
>> -        tablestr = _string.join(table, ' ')
>> -        # sometimes dmraid and dm have the disks of a mirror swapped
>> -        if self.rs.dmTable.type == "mirror":
>> -            tmp = table[8]
>> -            table[8] = table[10]
>> -            table[10] = tmp
>> -            alt_tablestr = _string.join(table, ' ')
>> +        # We do this to avoid the index out of range exception
>> +        if len(table1) != len(table2):
>> +            return False
>> +
>> +        # We parse the first section before the list of devs.
>> +        for i in range(len(table1)):
>> +            d1 = map_dev(table1[i])
>> +            d2 = map_dev(table2[i])
>> +
>> +            # when at least one changes its a device.
>> +            if (table1[i] != d1) or (table2[i] != d2):
>> +                # The d{1,2} will always have the major:minor string
>> +                # We also need what comes after the dev, the offset.
>> +                try:
>> +                    table1sets.append((d1, table1[i+1]))
>> +                    table2sets.append((d2, table2[i+1]))
>> +                    i += 1
>> +                except IndexError, msg:
>> +                    # The device must have an offset, if not its nonesense
>> +                    return False
>> +                continue
>> +
>> +            # these are not devices
>> +            if (table1[i] == d1) and (table2[i] == d2):
>
> This test is the logical complement of the one above, so since the if 
> block above ends in a continue, there is no need for this test.

This I already notice but left it there for readability.  Guess if we
leave the comment it will maintain its readability.  Will change.

>
>> +                if d1 == d2:
>> +                    continue
>> +
>> +                if d1 != d2:
>> +                    return False
>> +
>> +        # For mirror sets the devices might be in disorder.
>> +        if self.rs.type == "mirror":
>> +            for elem in table1sets:
>> +                if elem not in table2sets:
>> +                    return False
>> +
>
> This test is not 100% proof, what if table1 has 8:0 0, 8:0 0 and table 2 
> has 8:0 0, 8:16 0 ?
>
> I know this sounds very unlikely and should never happen, but still. Howabout:
> ###
> if self.rs.type == "mirror" and len(table1sets) == 2:
>     if table1sets[0] == table2sets[1] and table1sets[1] == table2sets[0]:
>         return True

This wont hold when there is a mirror with 3 devs.  Which I think is
equally unlikelly, but still....

will resend.

Thx for the review.

>
> for i in range(len(table1sets)):
>     if (table1sets[i][1] != table2sets[i][1]) or\
>         table1sets[i][2] != table2sets[i][2]:
>         return False
> ###
>
> Note that the mirror with non swapped disks is handled by the regular case here
>
>
>> +        # For none mirror the devs have to be in order.
>>          else:
>> -            alt_tablestr = None
>> +            for i in range(len(table1sets)):
>> +                if (table1sets[i][1] != table2sets[i][1]) or\
>> +                            table1sets[i][2] != table2sets[i][2]:
>> +                    return False
>> +
>> +        return True
>> +
>> +    def get_map(self):
>> +        if not self._RaidSet__map is None:
>> +            return self._RaidSet__map
>>           import dm as _dm
>>           for map in _dm.maps():
>>              # XXX wtf?  why's it have a space at the end sometimes?
>> -            if str(map.table).strip() == tablestr or alt_tablestr and \
>> -                   str(map.table).strip() == alt_tablestr:
>> +            if self.equal(str(map.table), str(self.rs.dmTable)):
>>                  self._RaidSet__map = map
>>                  self.active = True
>>                  del _dm
>
> Regards,
>
> Hans
>
> _______________________________________________
> Anaconda-devel-list mailing list
> Anaconda-devel-list@xxxxxxxxxx
> https://www.redhat.com/mailman/listinfo/anaconda-devel-list

-- 
Joel Andres Granados
Brno, Czech Republic, Red Hat.

_______________________________________________
Anaconda-devel-list mailing list
Anaconda-devel-list@xxxxxxxxxx
https://www.redhat.com/mailman/listinfo/anaconda-devel-list

[Index of Archives]     [Kickstart]     [Fedora Users]     [Fedora Legacy List]     [Fedora Maintainers]     [Fedora Desktop]     [Fedora SELinux]     [Big List of Linux Books]     [Yosemite News]     [Yosemite Photos]     [KDE Users]     [Fedora Tools]
  Powered by Linux