diff --git a/tools/mountstats/mountstats.py b/tools/mountstats/mountstats.py index 8e129c83..d488f9e1 100755 --- a/tools/mountstats/mountstats.py +++ b/tools/mountstats/mountstats.py @@ -333,6 +333,11 @@ class DeviceData: found = True self.__parse_rpc_line(words) + def fstype(self): + """Return the fstype for the mountpoint + """ + return self.__nfs_data['fstype'] + def is_nfs_mountpoint(self): """Return True if this is an NFS or NFSv4 mountpoint, otherwise return False @@ -953,73 +958,78 @@ def nfsstat_command(args): return 0 def print_iostat_summary(old, new, devices, time): + if len(devices) == 0: + print('No NFS mount points were found') + return + for device in devices: stats = DeviceData() stats.parse_stats(new[device]) - if not old or device not in old: + if old and device in old: + old_stats = DeviceData() + old_stats.parse_stats(old[device]) + if stats.fstype() == old_stats.fstype(): + stats.compare_iostats(old_stats).display_iostats(time) + else: # device is in old, but fstypes are different + stats.display_iostats(time) + else: # device is only in new stats.display_iostats(time) - else: - if ("fstype autofs" not in str(old[device])) and ("fstype autofs" not in str(new[device])): - old_stats = DeviceData() - old_stats.parse_stats(old[device]) - diff_stats = stats.compare_iostats(old_stats) - diff_stats.display_iostats(time) + +def list_nfs_mounts(givenlist, mountstats): + """return a list of NFS mounts given a list to validate or + return a full list if the given list is empty - + may return an empty list if none found + """ + devicelist = [] + if len(givenlist) > 0: + for device in givenlist: + if device in mountstats: + stats = DeviceData() + stats.parse_stats(mountstats[device]) + if stats.is_nfs_mountpoint(): + devicelist += [device] + else: + for device, descr in mountstats.items(): + stats = DeviceData() + stats.parse_stats(descr) + if stats.is_nfs_mountpoint(): + devicelist += [device] + return devicelist def iostat_command(args): """iostat-like command for NFS mount points """ mountstats = parse_stats_file(args.infile) - devices = [os.path.normpath(mp) for mp in args.mountpoints] + origdevices = [os.path.normpath(mp) for mp in args.mountpoints] if args.since: old_mountstats = parse_stats_file(args.since) else: old_mountstats = None - # make certain devices contains only NFS mount points - if len(devices) > 0: - check = [] - for device in devices: - stats = DeviceData() - try: - stats.parse_stats(mountstats[device]) - if stats.is_nfs_mountpoint(): - check += [device] - except KeyError: - continue - devices = check - else: - for device, descr in mountstats.items(): - stats = DeviceData() - stats.parse_stats(descr) - if stats.is_nfs_mountpoint(): - devices += [device] - if len(devices) == 0: - print('No NFS mount points were found') - return 1 - sample_time = 0 + # make certain devices contains only NFS mount points + devices = list_nfs_mounts(origdevices, mountstats) + print_iostat_summary(old_mountstats, mountstats, devices, sample_time) + if args.interval is None: - print_iostat_summary(old_mountstats, mountstats, devices, sample_time) return - if args.count is not None: - count = args.count - while count != 0: - print_iostat_summary(old_mountstats, mountstats, devices, sample_time) - old_mountstats = mountstats - time.sleep(args.interval) - sample_time = args.interval - mountstats = parse_stats_file(args.infile) + count = args.count + while True: + if count is not None: count -= 1 - else: - while True: - print_iostat_summary(old_mountstats, mountstats, devices, sample_time) - old_mountstats = mountstats - time.sleep(args.interval) - sample_time = args.interval - mountstats = parse_stats_file(args.infile) + if count == 0: + break + time.sleep(args.interval) + old_mountstats = mountstats + sample_time = args.interval + mountstats = parse_stats_file(args.infile) + # nfs mountpoints may appear or disappear, so we need to + # recheck the devices list each time we parse mountstats + devices = list_nfs_mounts(origdevices, mountstats) + print_iostat_summary(old_mountstats, mountstats, devices, sample_time) args.infile.close() if args.since: diff --git a/tools/nfs-iostat/nfs-iostat.py b/tools/nfs-iostat/nfs-iostat.py index 85294fb9..e46b1a83 100755 --- a/tools/nfs-iostat/nfs-iostat.py +++ b/tools/nfs-iostat/nfs-iostat.py @@ -187,6 +187,11 @@ class DeviceData: found = True self.__parse_rpc_line(words) + def fstype(self): + """Return the fstype for the mountpoint + """ + return self.__nfs_data['fstype'] + def is_nfs_mountpoint(self): """Return True if this is an NFS or NFSv4 mountpoint, otherwise return False @@ -471,41 +476,31 @@ def parse_stats_file(filename): return ms_dict def print_iostat_summary(old, new, devices, time, options): - stats = {} - diff_stats = {} - devicelist = [] - if old: - # Trim device list to only include intersection of old and new data, - # this addresses umounts due to autofs mountpoints - for device in devices: - if "fstype autofs" not in str(old[device]): - devicelist.append(device) - else: - devicelist = devices + display_stats = {} + + if len(devices) == 0: + print('No NFS mount points were found') + return - for device in devicelist: - stats[device] = DeviceData() - stats[device].parse_stats(new[device]) - if old: + for device in devices: + stats = DeviceData() + stats.parse_stats(new[device]) + if old and device in old: old_stats = DeviceData() old_stats.parse_stats(old[device]) - diff_stats[device] = stats[device].compare_iostats(old_stats) + if stats.fstype() == old_stats.fstype(): + display_stats[device] = stats.compare_iostats(old_stats) + else: # device is in old, but fstypes are different + display_stats[device] = stats + else: # device is only in new + display_stats[device] = stats if options.sort: - if old: - # We now have compared data and can print a comparison - # ordered by mountpoint ops per second - devicelist.sort(key=lambda x: diff_stats[x].ops(time), reverse=True) - else: - # First iteration, just sort by newly parsed ops/s - devicelist.sort(key=lambda x: stats[x].ops(time), reverse=True) + devices.sort(key=lambda x: display_stats[x].ops(time), reverse=True) count = 1 - for device in devicelist: - if old: - diff_stats[device].display_iostats(time, options.which) - else: - stats[device].display_iostats(time, options.which) + for device in devices: + display_stats[device].display_iostats(time, options.which) count += 1 if (count > options.list): @@ -520,10 +515,11 @@ def list_nfs_mounts(givenlist, mountstats): devicelist = [] if len(givenlist) > 0: for device in givenlist: - stats = DeviceData() - stats.parse_stats(mountstats[device]) - if stats.is_nfs_mountpoint(): - devicelist += [device] + if device in mountstats: + stats = DeviceData() + stats.parse_stats(mountstats[device]) + if stats.is_nfs_mountpoint(): + devicelist += [device] else: for device, descr in mountstats.items(): stats = DeviceData() @@ -592,11 +588,7 @@ client are listed. parser.add_option_group(displaygroup) (options, args) = parser.parse_args(sys.argv) - for arg in args: - - if arg == sys.argv[0]: - continue - + for arg in args[1:]: if arg in mountstats: origdevices += [arg] elif not interval_seen: @@ -622,47 +614,29 @@ client are listed. print('Illegal value %s' % arg) return - # make certain devices contains only NFS mount points - devices = list_nfs_mounts(origdevices, mountstats) - if len(devices) == 0: - print('No NFS mount points were found') - return - - old_mountstats = None sample_time = 0.0 + # make certain devices contains only NFS mount points + devices = list_nfs_mounts(origdevices, mountstats) + print_iostat_summary(old_mountstats, mountstats, devices, sample_time, options) + if not interval_seen: - print_iostat_summary(old_mountstats, mountstats, devices, sample_time, options) return - if count_seen: - while count != 0: - print_iostat_summary(old_mountstats, mountstats, devices, sample_time, options) - old_mountstats = mountstats - time.sleep(interval) - sample_time = interval - mountstats = parse_stats_file('/proc/self/mountstats') - # automount mountpoints add and drop, if automount is involved - # we need to recheck the devices list when reparsing - devices = list_nfs_mounts(origdevices,mountstats) - if len(devices) == 0: - print('No NFS mount points were found') - return + while True: + if count_seen: count -= 1 - else: - while True: - print_iostat_summary(old_mountstats, mountstats, devices, sample_time, options) - old_mountstats = mountstats - time.sleep(interval) - sample_time = interval - mountstats = parse_stats_file('/proc/self/mountstats') - # automount mountpoints add and drop, if automount is involved - # we need to recheck the devices list when reparsing - devices = list_nfs_mounts(origdevices,mountstats) - if len(devices) == 0: - print('No NFS mount points were found') - return + if count == 0: + break + time.sleep(interval) + old_mountstats = mountstats + sample_time = interval + mountstats = parse_stats_file('/proc/self/mountstats') + # nfs mountpoints may appear or disappear, so we need to + # recheck the devices list each time we parse mountstats + devices = list_nfs_mounts(origdevices, mountstats) + print_iostat_summary(old_mountstats, mountstats, devices, sample_time, options) # # Main