1. 06 Oct, 2016 1 commit
    • Mike Fleetwood's avatar
      Prevent the UI hanging while gpart data rescue is running (#772123) · aeebee9c
      Mike Fleetwood authored
      Running Device > Attempt Data Rescue... hangs the GParted UI for as long
      as gpart takes to scan the whole disk device looking for file system
      signatures.
      
      Originally when gpart support was added by commit [1] a separate thread
      was created to run gpart.  Then most threading was removed by commit [2]
      which left gpart running in the main thread blocking the UI.
      
      [1] ef37bdb7
          Added support to lost data recovery using gpart
      
      [2] 52a2a9b0
          Reduce threading (#685740)
      
      guess_partition_table() hand codes using Glib to run the gpart command
      asynchronously reading standard output, but it just doesn't run the Gtk
      main loop to process events, hence the UI hangs.  Instead just use
      Utils::execute_command() which handles everything already.  It runs the
      commands asynchronously, reading output and if being run in the main
      thread also calls the Gtk main loop to keep the UI responsive.
      
      Bug 772123 - GParted is unresponsive while gpart is running
      aeebee9c
  2. 14 Sep, 2016 1 commit
    • Mike Fleetwood's avatar
      Remove out of date comment from the end of set_devices_thread() · ab4040c5
      Mike Fleetwood authored
      The comment became completely unnecessary with the transfer of
      mount_info and fstab_info into separate Mount_Info module by commit:
          63ec73df
          Split mount_info and fstab_info maps into separate Mount_Info module
      
      It was never necessary to clear one of the mappings at the end of the
      device refresh because it was reloaded at the start of the next device
      refresh anyway and it is only a small amount of memory.
      ab4040c5
  3. 06 Aug, 2016 13 commits
    • Mike Fleetwood's avatar
      Remove no longer needed includes from GParted_Core.cc · e6f4b1c3
      Mike Fleetwood authored
      No longer needed since commit:
          504eb04d
          Roll back (remove) code to recognize /dev/mapper/* devices, because ...
      e6f4b1c3
    • Mike Fleetwood's avatar
      Split mount_info and fstab_info maps into separate Mount_Info module · 63ec73df
      Mike Fleetwood authored
      The GParted_Core::mount_info and GParted_Core::fstab_info maps and the
      methods that manipulate them are self-contained.  Therefore move them to
      a separate Mount_Info module and reduce the size of the monster
      GParted_Core slightly.
      63ec73df
    • Mike Fleetwood's avatar
      Switch to static class interface for FS_Info · a94be2da
      Mike Fleetwood authored
      The FS_Info module has a pseudo multi-object interface and used the
      constructor to load the cache.  However all the data in the class is
      static.  An FS_Info object doesn't contain any member variables, yet was
      needed just to call the member functions.
      
      Make all the member functions static removing the need to use any
      FS_Info objects and provide an explicit load_cache() method.
      a94be2da
    • Mike Fleetwood's avatar
      Switch to a static interface for Proc_Partitions_Info · 912766c2
      Mike Fleetwood authored
      The Proc_Partitions_Info has a pseudo multi-object interface and uses
      the constructor to load the cache.  However all the data in the class is
      static.  A Proc_Partitions_Info object doesn't contain any member
      variables, yet was needed just to call the member functions.
      
      Make all the member functions static removing the need to use any
      Proc_Partitions_Info objects and provide and explicit load_cache()
      method.
      912766c2
    • Mike Fleetwood's avatar
      Pre-populate BlockSpecial cache while reading /proc/partitions (#767842) · 571304d2
      Mike Fleetwood authored
      GParted is already reading /proc/partitions to get whole disk device
      names.  The file also contains the major, minor device number of every
      partition.  Use this information to pre-populate the cache in the
      BlockSpecial class.
      
          # cat /proc/partitions
          major minor  #blocks  name
      
             8        0   20971520 sda
             8        1     512000 sda1
             8        2   20458496 sda2
          ...
             9        3    1047552 md3
           259        2     262144 md3p1
           259        3     262144 md3p2
          ...
           253        0   18317312 dm-0
           253        1    2097152 dm-1
           253        2    8383872 dm-2
           253        3    1048576 dm-3
      
      Note that for Device-Mapper names (dm-*) the kernel is not using the
      canonical user space names (mapper/*).  There is no harm in
      pre-populating the cache with these names and will help if tools report
      them too.  It is just that for DMRaid, LVM and LUKS, GParted uses the
      canonical /dev/mapper/* names so will still have to call stat() once for
      each such name.
      
      For plain disks (sd*) and Linux Software RAID arrays (md*) the kernel
      name is the common user space name too, therefore matches what GParted
      uses and pre-populating does avoid calling stat() at all for these
      names.
      
      Bug 767842 - File system usage missing when tools report alternate block
                   device names
      571304d2
    • Mike Fleetwood's avatar
      Cache looked up major, minor numbers in BlockSpecial class (#767842) · 003d6eff
      Mike Fleetwood authored
      Creation of every BlockSpecial object used to result in a stat() OS
      call.  On one of my test VMs debugging with 4 disks and a few partitions
      on each, GParted refresh generated 541 calls to stat() in the
      BlockSpecial(name) constructor.  However there were only 45 unique
      names.  So on average each name was stat()ed approximately 12 times.
      
      Cache the major, minor number associated with each name after starting
      with a cleared cache for each GParted refresh.  This reduces these
      direct calls to stat() to just the 45 unique names.
      
      Bug 767842 - File system usage missing when tools report alternate block
                   device names
      003d6eff
    • Mike Fleetwood's avatar
      Overload is_dev_mounted() function (#767842) · e4a8530b
      Mike Fleetwood authored
      Small optimisation which avoids constructing an extra BlockSpecial
      object when determining if a btrfs member is mounted.  Rather than
      extracting the name from the BlockSpecial object in
      btrfs::get_mount_device() and re-constructing another BlockSpecial
      object from that name in GParted_Core::is_dev_mounted(), pass the
      BlockSpecial object directly.
      
      Bug 767842 - File system usage missing when tools report alternate block
                   device names
      e4a8530b
    • Mike Fleetwood's avatar
      Add BlockSpecial into mount_info and fstab_info (#767842) · a800ca8b
      Mike Fleetwood authored
      On some distributions having btrfs on top of LUKS encrypted partitions,
      adding a second device and removing the first device used to mount the
      file system causes GParted to no longer be able to report the file
      system as busy or the mount points themselves.
      
      For example, on CentOS 7, create a single btrfs file system and mount
      it.  The provided /dev/mapper/sdb1_crypt name is reported, via
      /proc/mounts, as the mounting device:
          # cryptsetup luksFormat --force-password /dev/sdb1
          # cryptsetup luksOpen /dev/sdb1 sdb1_crypt
          # mkfs.btrfs -L encrypted-btrfs /dev/mapper/sdb1_crypt
          # mount /dev/mapper/sdb1_crypt /mnt/1
      
          # ls -l /dev/mapper
          total 0
          lrwxrwxrwx. 1 root root       7 Jul  2 14:15 centos-root -> ../dm-1
          lrwxrwxrwx. 1 root root       7 Jul  2 14:15 centos-swap -> ../dm-0
          crw-------. 1 root root 10, 236 Jul  2 14:15 control
          lrwxrwxrwx. 1 root root       7 Jul  2 15:14 sdb1_crypt -> ../dm-2
          # fgrep btrfs /proc/mounts
          /dev/mapper/sdb1_crypt /mnt/1 btrfs rw,seclabel,relatime,space_cache 0 0
      
      Add a second device to the btrfs file system:
          # cryptsetup luksFormat --force-password /dev/sdb2
          # cryptsetup luksOpen /dev/sdb2 sdb2_crypt
          # btrfs device add /dev/mapper/sdb2_crypt /mnt/1
      
          # ls -l /dev/mapper
          ...
          lrwxrwxrwx. 1 root root       7 Jul  2 15:12 sdb2_crypt -> ../dm-3
          # btrfs filesystem show /dev/mapper/sdb1_crypt
          Label: 'encrypted-btrfs'  uuid: 45d7b1ef-820c-4ef8-8abd-c70d928afb49
                  Total devices 2 FS bytes used 32.00KiB
                  devid    1 size 1022.00MiB used 12.00MiB path /dev/mapper/sdb1_crypt
                  devid    2 size 1022.00MiB used 0.00B path /dev/mapper/sdb2_crypt
      
      Remove the first mounting device from the btrfs file system.  Now the
      non-canonical name /dev/dm-3 is reported, via /proc/mounts, as the
      mounting device:
          # btrfs device delete /dev/mapper/sdb1_crypt /mnt/1
      
          # btrfs filesystem show /dev/mapper/sdb2_crypt
          Label: 'encrypted-btrfs'  uuid: 45d7b1ef-820c-4ef8-8abd-c70d928afb49
                  Total devices 1 FS bytes used 96.00KiB
                  devid    2 size 1022.00MiB used 144.00MiB path /dev/mapper/sdb2_crypt
          # fgrep btrfs /proc/mounts
          /dev/dm-3 /mnt/1 btrfs rw,seclabel,relatime,space_cache 0 0
          # ls -l /dev/dm-3
          brw-rw----. 1 root disk 253, 3 Jul  2 15:12 /dev/dm-3
      
      GParted loads the mount_info mapping from /proc/mounts and with it the
      /dev/dm-3 name.  When GParted is determining if the encrypted btrfs file
      system is mounted or getting the mount points it is using the
      /dev/mapper/sdb2_crypt name.  Therefore no information is found and the
      file system is incorrectly reported as unmounted.
      
      Fix by changing mount_info and fstab_info to use BlockSpecial objects
      instead of strings so that matching is performed by major, minor device
      numbers rather than by string compare.  Note that as BlockSpecial
      objects are used as the key of std::map [1] mappings operator<() [2]
      needs to be provided to order the key values.
      
      [1] std::map
          http://www.cplusplus.com/reference/map/map/
      [2] std::map::key_comp
          http://www.cplusplus.com/reference/map/map/key_comp/
      
      Bug 767842 - File system usage missing when tools report alternate block
                   device names
      a800ca8b
    • Mike Fleetwood's avatar
      Rename Partition::add_path() to set_path() (#767842) · 40f39bdb
      Mike Fleetwood authored
      To reflect that there is now only a single path in the Partition object
      now.  Also get rid of the now unneeded optional clear_paths parameter
      which was only relevant when there was a vector of paths.
      
      Bug 767842 - File system usage missing when tools report alternate block
                   device names
      40f39bdb
    • Mike Fleetwood's avatar
      Update calibrate_partition() for single partition path (#767842) · 54652b0d
      Mike Fleetwood authored
      Now that Partition objects only have a single path, rather than a list
      of paths, stop performing unnecessary actions in calibrate_partitions()
      which added alternate paths reported from libparted.  Just left with
      setting the partition path name correctly, when the path name doesn't
      exist.  Happens when the path is set to "Copy of /dev/SRC" when the
      partition was newly created by a copy-paste into unallocated space
      earlier in the sequence of operations now being applied.
      
      Bug 767842 - File system usage missing when tools report alternate block
                   device names
      54652b0d
    • Mike Fleetwood's avatar
      Simplify Partition object to a single path (#767842) · 214255ed
      Mike Fleetwood authored
      Change from a vector of paths to a single path member in the Partition
      object.  Remove add_paths() and get_paths() methods.  Keep add_path()
      and get_path().
      
      Bug 767842 - File system usage missing when tools report alternate block
                   device names
      214255ed
    • Mike Fleetwood's avatar
      Rename Device::add_path() to set_path() (#767842) · 1dc8a0c6
      Mike Fleetwood authored
      To reflect that there is only a single path in the Device object now.
      Also get rid of the now unneeded optional parameter which was only
      relevant when there was a vector of paths.
      
      Bug 767842 - File system usage missing when tools report alternate block
                   device names
      1dc8a0c6
    • Mike Fleetwood's avatar
      Simplify Device object to a single path (#767842) · 902afaa0
      Mike Fleetwood authored
      Background
      
      GParted stored a list of paths for Device and Partition objects.  It
      sorted this list [1][2] and treated the first specially as that is what
      get_path() returned and was used almost everywhere; with the file system
      specific tools, looked up in various *_Info caches, etc.
      
      [1] Device::add_path(), ::add_paths()
      [2] Partition::add_path(), ::add_paths()
      
      Mount point display [3] was the only bit of GParted which really worked
      with the path list.  Busy file system detection [4] just used the path
      provided by libparted, or for LUKS /dev/mapper/* names.  It checked that
      single path against the mounted file systems found from /proc/mounts,
      expanded with additional block device names when symlinks were
      encountered.
      
      [3] GParted_Core::set_mountpoints() -> set_mountpoints_helper()
      [4] GParted_Core::set_device_partitions() -> is_busy()
          GParted_Core::set_device_one_partition() -> is_busy()
          GParted_Core::set_luks_partition() -> is_busy()
      
      Having the first path, by sort order, treated specially by being used
      everywhere and virtually ignoring the others was wrong, complicated to
      remember and difficult code with.  As all the additional paths were
      virtually unused and made no difference, remove them.  The "improved
      detection of mountpoins, free space, etc.." benefit from commit [5]
      doesn't seem to exist.  Therefore simplify to a single path for Device
      and Partition objects.
      
      [5] commit 6d8b169e
          changed the way devices and partitions store their device paths.
          Instead of holding a 'realpath' and a symbolic path we store paths
          in a list.  This allows for improved detection of mountpoins, free
          space, etc..
      
      This patch
      
      Simplify the Device object from a vector of paths to a single path.
      Remove add_paths() and get_paths() methods.  Keep add_path() and
      get_path() for now.
      
      Bug 767842 - File system usage missing when tools report alternate block
                   device names
      902afaa0
  4. 15 Jun, 2016 1 commit
  5. 30 May, 2016 1 commit
    • Mike Fleetwood's avatar
      Stop leaking PedGeometry object memory (#767009) · 3724421e
      Mike Fleetwood authored
      Calling libparted ped_geometry_new() creates a new PedGeometry object
      from malloced memory, however the corresponding ped_geometry_destroy()
      is never called to destroy the object and free the memory.
      
      Perform a resize of a FAT file system when running GParted under
      valgrind identifies several memory blocks leaked via ped_geometry_new()
      from resize_move_filesystem_using_libparted().  One such example:
      
          # valgrind --track-origins=yes --leak-check=full ./gpartedbin
          ...
          ==32069== 32 bytes in 1 blocks are definitely lost in loss record 5,419 of 11,542
          ==32069==    at 0x4C29BFD: malloc (in /usr/lib64/valgrind/vgpreload_memcheck-amd64-linux.so)
          ==32069==    by 0x8ECD8C5: ped_malloc (libparted.c:231)
          ==32069==    by 0x8ED23C1: ped_geometry_new (geom.c:79)
          ==32069==    by 0x4764F3: GParted::GParted_Core::resize_move_filesystem_using_libparted(GParted::Partition const&, GParted::Partition const&, GParted::OperationDetail&) (GParted_Core.cc:2666)
          ==32069==    by 0x478007: GParted::GParted_Core::resize_filesystem(GParted::Partition const&, GParted::Partition const&, GParted::OperationDetail&, bool) (GParted_Core.cc:2990)
          ==32069==    by 0x478440: GParted::GParted_Core::maximize_filesystem(GParted::Partition const&, GParted::OperationDetail&) (GParted_Core.cc:3037)
          ==32069==    by 0x4769A0: GParted::GParted_Core::resize(GParted::Partition const&, GParted::Partition const&, GParted::OperationDetail&) (GParted_Core.cc:2746)
          ==32069==    by 0x47582B: GParted::GParted_Core::resize_move(GParted::Partition const&, GParted::Partition&, GParted::OperationDetail&) (GParted_Core.cc:2457)
          ==32069==    by 0x46DDB2: GParted::GParted_Core::apply_operation_to_disk(GParted::Operation*) (GParted_Core.cc:767)
          ...
      
      There is also a leak of a PedGeometry object from
      resize_move_partition().  Fix by calling ped_geometry_destroy() to
      delete all the allocated PedGeometry objects and free the memory.
      
      Bug 767009 - PedGeometry objects are memory leaked
      3724421e
  6. 20 May, 2016 3 commits
    • Mike Fleetwood's avatar
      Replace whole path list after calibrate in apply_operation_to_disk() (#766349) · ab923121
      Mike Fleetwood authored
      When replacing the list of paths for the other partition object involved
      in either a Resize/Move or Format operation in apply_operation_to_disk()
      should replace the whole list of partitions not just replace with the
      first path.  Copy the whole path list is the correct action.  It makes
      no material difference because secondary partition paths are only used
      to discover mount points during refresh phase and not at the apply
      phase, where only the primary path is used.
      
      Bug 766349 - Resolve code ugliness with partition path getting set to
                   "copy of /dev/SRC"
      ab923121
    • Mike Fleetwood's avatar
      Stop relying on sort order when adding real paths in calibrate (#766349) · b77fef0d
      Mike Fleetwood authored
      Quoting the relevant comments from GParted_Core::calibrate_partition():
          Re-add the real partition path from libparted.
      
          When creating a copy operation by pasting into unallocated space the
          list of paths for the partition object was set to
          ["Copy of /dev/SRC"] because the partition didn't yet exist before
          the operations were applied.  Additional operations on that new
          partition also got the list of paths set to ["Copy of /dev/SRC"].
          This re-adds the real path to the start of the list making it
          ["/dev/NEW", "Copy of /dev/SRC"].  This provides the real path for
          file system specific tools used during those additional operations
          such mkfs for the format operation or fsck and others for the
          resize/move operation.
      
          FIXME: Having this work just because "/dev/NEW" happens to sort
          before "Copy of /dev/SRC" is ugly!  Probably have a separate display
          path which can be changed at will without affecting the list of real
          paths for the partition.
      
      Having a separate display path is overly complicated and unnecessary.
      Just replace the list of paths with the real one reported by libparted
      if it contained "Copy of /dev/SRC", determined by checking if the file
      exists.  Otherwise continue to add the libparted name as an alternate
      path.  Whole disk devices can never be named "Copy of /dev/SRC" because
      they are not partitioned so never created or deleted by GParted, only
      ever written to, hence don't need the extra exists test logic.
      
      Bug 766349 - Resolve code ugliness with partition path getting set to
                   "copy of /dev/SRC"
      b77fef0d
    • Mike Fleetwood's avatar
      Stop overriding real path when pasting into existing partitions (#766349) · 302cc804
      Mike Fleetwood authored
      When composing a copy operation it always named the destination
      partition as "copy of /dev/SRC".  For the case of pasting into
      unallocated space creating a new partition this was the right thing to
      do as the partition doesn't yet exist so the path is not yet known.
      However for the case of pasting into an existing partition the path is
      known and replacing it with "copy of /dev/SRC" is wrong.  No other
      operation when operating on an existing partition changes it path.
      
      Given a set of existing partitions, sdb1 to sdb4, compose a set of copy
      operations as: copy sdb1 to sdb2, copy sdb2 to sdb3 and copy sdb3 to
      sdb4.  The displayed partitions before being applied become:
          /dev/sdb1
          copy of /dev/sdb1
          copy of copy of /dev/sdb1
          copy of copy of copy of /dev/sdb1
      And the pending operations are named:
          Copy /dev/sdb1 to /dev/sdb2
          Copy copy of /dev/sdb1 to /dev/sdb3
          Copy copy of copy of /dev/sdb1 to /sev/sdb4
      
      This is perverse.  In the case of pasting into an existing partition
      keep the real path name.  This keeps the partitions being displayed as:
          /dev/sdb1
          /dev/sdb2
          /dev/sdb3
          /dev/sdb4
      And the pending operations named as:
          Copy /dev/sdb1 to /dev/sdb2
          Copy /dev/sdb2 to /dev/sdb3
          Copy /dev/sdb3 to /dev/sdb4
      Much more understandable.
      
      Also switch to an upper case "C" in "Copy of /dev/SRC" as the temporary
      path name when pasting into unallocated space.  Finally update the
      comment in calibrate_partition() to describe the remaining cases when
      re-adding the path is still required.
      
      Bug 766349 - Resolve code ugliness with partition path getting set to
                   "copy of /dev/SRC"
      302cc804
  7. 18 Apr, 2016 2 commits
    • Mike Fleetwood's avatar
      Add symbolic constants SETTLE_DEVICE_*_MAX_WAIT_SECONDS · 94979a38
      Mike Fleetwood authored
      Make the code a little more self documenting by adding the symbolic
      constants:
          SETTLE_DEVICE_APPLY_MAX_WAIT_SECONDS
          SETTLE_DEVICE_PROBE_MAX_WAIT_SECONDS
      which highlight that settle_device() is called in two different
      contexts, device probe and apply operations, with two different timeout
      values.
      94979a38
    • Mike Fleetwood's avatar
      Wait for udev to recreate /dev/PTN entries when calibrating (#762941) · fd9013d5
      Mike Fleetwood authored
      File system specific commands sometimes fail reporting that the
      partition specific /dev entry doesn't exist.  Example failing check
      operation details:
      
          Check and repair file system (ext4) on dev/sdb4
            calibrate /dev/sdb4
              path: /dev/sdb4 (partition)
              start: 4196352
              end: 6293503
              size: 2097152 (1.00 GiB)
            check file system on /dev/sdb4 for errors and (if possible) fix them
              e2fsck -f -y -bv -C 0 /dev/sdb4
                e2fsck 1.42.9 (28-Dec-2013)
                e2fsck: No such file or directory while trying to open /dev/sdb4
                Possibly non-existent device?
      
      This has been reproduced on CentOS 7.  Debugging shows that the
      libparted calls used to re-read the partition details in
      GParted_Core::calibrate_partition() leads to udev removing and re-adding
      all the partition /dev entries for the disk.
      
          # udevadm monitor &
          # gpartedbin
          ...
           16.480662 +12.618659 calibrate_partition()          calling get_device("/dev/sdb", lp_device) ...
           16.483644 +0.002982 calibrate_partition()          get_device() returned
           16.483678 +0.000034 calibrate_partition()          calling get_disk(lp_device, lp_disk) ...
           16.618113 +0.134435 calibrate_partition()          get_disk() returned
          KERNEL[19275.707968] remove   /devices/pci0000:00/0000:00:0d.0/ata4/host3/target3:0:0/3:0:0:0/block/sdb/sdb1 (block)
           16.618561 +0.000448 destroy_device_and_disk()      calling ped_disk_destroy(lp_disk) ...
           16.618584 +0.000023 destroy_device_and_disk()      ped_disk_destroy() returned
           16.618591 +0.000007 destroy_device_and_disk()      calling ped_device_destroy(lp_disk) ...
           16.618602 +0.000011 destroy_device_and_disk()      ped_device_destroy() returned
           16.618687 +0.000085 calibrate_partition()          return true
           16.618851 +0.000164 execute_command()              e2fsck -f -y -v -C 0 /dev/sdb4
          KERNEL[19275.708389] remove   /devices/pci0000:00/0000:00:0d.0/ata4/host3/target3:0:0/3:0:0:0/block/sdb/sdb2 (block)
          KERNEL[19275.708500] remove   /devices/pci0000:00/0000:00:0d.0/ata4/host3/target3:0:0/3:0:0:0/block/sdb/sdb3 (block)
          KERNEL[19275.708643] remove   /devices/pci0000:00/0000:00:0d.0/ata4/host3/target3:0:0/3:0:0:0/block/sdb/sdb4 (block)
          KERNEL[19275.768278] change   /devices/pci0000:00/0000:00:0d.0/ata4/host3/target3:0:0/3:0:0:0/block/sdb (block)
          KERNEL[19275.771171] add      /devices/pci0000:00/0000:00:0d.0/ata4/host3/target3:0:0/3:0:0:0/block/sdb/sdb1 (block)
          KERNEL[19275.771360] add      /devices/pci0000:00/0000:00:0d.0/ata4/host3/target3:0:0/3:0:0:0/block/sdb/sdb2 (block)
          KERNEL[19275.771542] add      /devices/pci0000:00/0000:00:0d.0/ata4/host3/target3:0:0/3:0:0:0/block/sdb/sdb3 (block)
          KERNEL[19275.775858] add      /devices/pci0000:00/0000:00:0d.0/ata4/host3/target3:0:0/3:0:0:0/block/sdb/sdb4 (block)
          UDEV  [19275.820153] remove   /devices/pci0000:00/0000:00:0d.0/ata4/host3/target3:0:0/3:0:0:0/block/sdb/sdb3 (block)
          UDEV  [19275.823152] remove   /devices/pci0000:00/0000:00:0d.0/ata4/host3/target3:0:0/3:0:0:0/block/sdb/sdb4 (block)
          UDEV  [19275.828275] remove   /devices/pci0000:00/0000:00:0d.0/ata4/host3/target3:0:0/3:0:0:0/block/sdb/sdb1 (block)
           16.742735 +0.123884 execute_command()              exit status 8
          UDEV  [19275.841425] remove   /devices/pci0000:00/0000:00:0d.0/ata4/host3/target3:0:0/3:0:0:0/block/sdb/sdb2 (block)
          UDEV  [19275.905478] change   /devices/pci0000:00/0000:00:0d.0/ata4/host3/target3:0:0/3:0:0:0/block/sdb (block)
          UDEV  [19276.013580] add      /devices/pci0000:00/0000:00:0d.0/ata4/host3/target3:0:0/3:0:0:0/block/sdb/sdb3 (block)
          UDEV  [19276.034728] add      /devices/pci0000:00/0000:00:0d.0/ata4/host3/target3:0:0/3:0:0:0/block/sdb/sdb4 (block)
          UDEV  [19276.174840] add      /devices/pci0000:00/0000:00:0d.0/ata4/host3/target3:0:0/3:0:0:0/block/sdb/sdb1 (block)
          UDEV  [19276.237105] add      /devices/pci0000:00/0000:00:0d.0/ata4/host3/target3:0:0/3:0:0:0/block/sdb/sdb2 (block)
      
      So exactly when GParted is running the external e2fsck command, udev is
      in the middle of removing and re-adding all the /dev partition entries
      for the disk.  Hence the above failure reporting that /dev/sdb4 didn't
      exist.  This error depends on the timing between GParted running the
      external file system specific command and udev removing and re-adding
      the entries, so sometimes it works and sometimes it fails.
      
      Further debugging showed that simply opening and closing the whole disk
      device read-write triggers the same removing and re-adding of all the
      partition /dev entries with udev >= 219.  Opening the whole disk device
      read-write is what libparted has always done until this post
      libparted 3.2 patch to make it open read-only when probing:
      
          http://git.savannah.gnu.org/cgit/parted.git/commit/?id=44d5ae0115c4ecfe3158748309e9912c5aede92d
          libparted: Use read only when probing devices on linux (#1245144)
      
      To fix this simply wait for udev devices to settle in
      calibrate_partitions().  The longest I have seen udev take to do this is
      0.80 seconds in a VM.  Wait up to 10 seconds as is done in commit() ->
      commit_to_os(), also called when applying operations.
      
      On configurations which don't have this issue execution of udevadm
      settle, which will return immediately, adds at most 0.1 seconds to the
      time taken for the calibrate step.  This won't be noticed in the time
      taken of the operation details so there is no point in trying to avoid
      executing udevadm settle when not needed.
      
      Bug 762941 - Operations sometimes failing with: No such file or
                   directory
      fd9013d5
  8. 07 Apr, 2016 1 commit
    • Mike Fleetwood's avatar
      Use realpath() safely (#764369) · d04826cc
      Mike Fleetwood authored
      realpath(3) manual page says:
      
          BUGS
              The POSIX.1-2001 standard version of this function is broken by
              design, since it is impossible to determine a suitable size for
              the output buffer, resolved_path.  According to POSIX.1-2001 a
              buffer of size PATH_MAX suffices, but PATH_MAX need not be a
              defined constant, and may have to be obtained using pathconf(3).
              And asking pathconf(3) does not really help, since, on the one
              hand POSIX warns that the result of pathconf(3) may be huge and
              unsuitable for mallocing memory, and on the other hand
              pathconf(3) may return -1 to signify that PATH_MAX is not
              bounded.  The resolved_path == NULL feature, not standardized in
              POSIX.1-2001, but standardized in POSIX.1-2008, allows this
              design problem to be avoided.
      
      The resolved_path == NULL feature of realpath() has existed as a Glibc
      extension since realpath() was first added to Glibc 1.90, released in
      June 1996.  Therefore it can be used unconditionally.
      
          https://sourceware.org/git/?p=glibc.git;a=commitdiff;h=fa0bc87c32d02cd81ec4d0ae00e0d943c683e6e1
      
      Bug 764369 - Use realpath() safely
      d04826cc
  9. 23 Feb, 2016 1 commit
    • Mike Fleetwood's avatar
      Use a single progress bar for the internal block copy operation (#762367) · 1358a5f4
      Mike Fleetwood authored
      As part of the internal block copy operation 5 initial ranges of blocks
      are copied using different block sizes to determine the fastest.  Then
      the remainder is copied using the fastest block size.  Each of these
      copies reports progress independently, so during the benchmarking phase
      the progress bar flashes 5 times as it goes from 0 to 100% in a fraction
      of a second, before showing the progress of the remainder.
      
      This looks bad, so report a single progress bar for all the ranges of
      blocks copied in a single copy operation.
      
      Already have variables done and length which track progress within each
      copied range; and total_done which records amount copied in previous
      ranges.  Just add total_length to allow overall progress to be reported.
      
      Bug 762367 - Use a single progress bar for the whole of the internal
                   copy operation
      1358a5f4
  10. 29 Jan, 2016 12 commits
    • Mike Fleetwood's avatar
      Prevent incorrect no usage values warning for luks/unknown (#760080) · 40c2cdda
      Mike Fleetwood authored
      Create and open a LUKS mapping but don't create any file system within.
      
          # cryptsetup luksFormat /dev/sdb5
          # cryptsetup luksOpen /dev/sdb5 sdb5_crypt
      
      GParted was incorrectly reporting this warning:
      
          Unable to read the contents of this file system!
          Because of this some operations may be unavailable.
          The cause might be a missing software package.
          The following list of software packages is required for luks file
          system support:  dmsetup.
      
      This is even though the usage figures for the on disk LUKS encryption
      are fully known.  See luks::set_used_sectors().
      
      This was occurring because derived PartitionLUKS::set_usage_known()
      was checking usage figures for the outer LUKS and the inner encrypted
      file system, unknown in this case.  Correct when displaying figures in
      the UI, but not correct in GParted_Core::set_used_sectors() when only
      checking the outer LUKS usage figures were set correctly.  Fix this.
      
      Bug 760080 - Implement read-only LUKS support
      40c2cdda
    • Mike Fleetwood's avatar
      Remove LUKS unsupported warning (#760080) · 97466810
      Mike Fleetwood authored
      Bug 760080 - Implement read-only LUKS support
      97466810
    • Mike Fleetwood's avatar
      Display messages for encrypted file systems (#760080) · 2d910494
      Mike Fleetwood authored
      At the moment any messages for an encrypted file system aren't shown,
      only messages from the outer PartitionLUKS object are shown.  Also in
      Win_GParted::activate_paste() the selected Partition object, possibly
      a derived PartitionLUKS, is cloned and the messages cleared.
      
      Therefore a set of accessor methods must be provided to query and modify
      partition messages.  Messages will be stored in the Partition object to
      which they are added and retrieved from all.  So in the case of a
      derived PartitionLUKS they will be retrieved from the messages vector of
      the PartitionLUKS object itself and the messages vector for the
      encrypted file system it contains.
      
      To replace code like this in GParted_Core:
      
          partition_temp->messages = messages;
      
      We might naturally provide a set_messages() method which assigns the
      messages vector and is used like this:
      
          partition_temp->set_messages( messages );
      
      However on a PartitionLUKS object what should set_messages() do?  By the
      name it will replace any existing messages in the PartitionLUKS object
      itself, but what should happen to the messages for the contained
      encrypted Partition object?  Should they be cleared or left alone?
      Rather than implement set_messages() with unclear semantics implement
      append_messages(), which in the PartitionLUKS object case will clearly
      leave any messages for the contained encrypted Partition object alone.
      Append_messages() is then used to add messages as the Partition or
      PartitionLUKS objects when populating the data in GParted_Core.
      
      Bug 760080 - Implement read-only LUKS support
      2d910494
    • Mike Fleetwood's avatar
      Populate encrypted Partition member inside PartitionLUKS (#760080) · c9a2986f
      Mike Fleetwood authored
      When there exists an open dm-crypt mapping, populate the encrypted
      Partition object representing the encrypted file system.
      
      Bug 760080 - Implement read-only LUKS support
      c9a2986f
    • Mike Fleetwood's avatar
      Add PartitionLUKS class and create objects (#760080) · 99ff0c76
      Mike Fleetwood authored
      Absolute minimum implementation of a PartitionLUKS class which can be
      constructed, polymorphically copied and destroyed.  Contains an
      "encrypted" member of type Partition to represent the encrypted file
      system within the LUKS format.
      
      Create PartitionLUKS objects instead of base Partition objects when a
      LUKS formatted partition is found.  Only the base Partition object
      member values have been populated, and the "encrypted" member remains
      blank at this point.
      
      Bug 760080 - Implement read-only LUKS support
      99ff0c76
    • Mike Fleetwood's avatar
      Refactor set_used_sectors() to be called per partition (#760080) · 9fee0c57
      Mike Fleetwood authored
      This is the equivalent change as made to set_mountpoints() in an earlier
      commit.  Change GParted_Core::set_used_sectors() from being called with
      a vector of partitions and processing them all to being called per
      partition.  This is in preparation for calling set_used_sectors() on a
      single Partition object inside a PartitionLUKS object.
      
      Bug 760080 - Implement read-only LUKS support
      9fee0c57
    • Mike Fleetwood's avatar
      Populate active LUKS mountpoints with /dev/mapper/NAME entry (#760080) · e9b893b4
      Mike Fleetwood authored
      Populate the canonical device name, /dev/mapper/NAME, used to access the
      encrypted file system into the mount points of the Partition object.
      This is the equivalent of what is already done for the Volume Group name
      and SWRaid Array device.
      
      This does get displayed in the Mount Point column in the main window,
      which isn't wanted.  However the data will be needed when displaying
      details of the encryption mapping in the Information dialog.  Both will
      be dealt with in following commits.
      
      Bug 760080 - Implement read-only LUKS support
      e9b893b4
    • Mike Fleetwood's avatar
      Refactor set_mountpoints() to be called per partition (#760080) · 1b731b93
      Mike Fleetwood authored
      Previously GParted_Core::set_mountpoints() was called with a vector of
      partitions and processed them all.  Now make set_mountpoints() process a
      single partition and push the calls to it down one level from
      set_devices_thread() into set_device_partitions() and
      set_device_one_partition().  This is in preparation for having an
      encrypted file system represented as a Partition object inside a
      PartitionLUKS object and needing to call set_mountpoints() for the inner
      single Partition object.
      
      Bug 760080 - Implement read-only LUKS support
      1b731b93
    • Mike Fleetwood's avatar
      Implement demand loading of LUKS_Info cache (#760080) · 13209126
      Mike Fleetwood authored
      Only load the LUKS_Info cache of active dm-crypt mappings when the first
      LUKS partition is encountered.  Not needed from a performance point of
      view as the longest that I have ever seen "dmsetup table --target crypt"
      take to run is 0.05 seconds.  Just means that the dmsetup command is
      only run when there are LUKS partitions and the information is needed.
      
      Bug 760080 - Implement read-only LUKS support
      13209126
    • Mike Fleetwood's avatar
      Add loading of LUKS mapping offset and length (#760080) · 317e4440
      Mike Fleetwood authored
      Also load the starting offset and length of the active dm-crypt mapping
      into the LUKS_Info module from the dmsetup output.  This provides the
      location and size of the encrypted data within the underlying block
      device.
      
      Note that dmsetup reports in units of 512 bytes sectors [1], the GParted
      LUKS_Info module uses bytes and GParted Partition objects work in device
      sector size units.  However the actual sector size of a dm-crypt mapping
      [2] is the same as that of the underlying block device [3].
      
          # modprobe scsi_debug dev_size_mb=128 sector_size=4096
          # fgrep scsi_debug /sys/block/*/device/model
          /sys/block/sdd/device/model:scsi_debug
          # parted /dev/sde print
          Error: /dev/sde: unrecognised disk label
          Model: Linux scsi_debug (scsi)
          Disk /dev/sde: 134MB
      [3] Sector size (logical/physical): 4096B/4096B
          Partition Table: unknown
      
          # cryptsetup luksFormat /dev/sde
          # cryptsetup luksOpen /dev/sde sde_crypt
          # parted /dev/mapper/sde_crypt print
          Error: /dev/mapper/sde_crypt: unrecognised disk label
          Model: Linux device-mapper (crypt) (dm)
          Disk /dev/mapper/sde_crypt: 132MB
      [2] Sector size (logical/physical): 4096B/4096B
          Partition Table: unknown
      
          # cryptsetup status sde_crypt
          /dev/mapper/sde_crypt is active.
            type:  LUKS1
            cipher:  aes-cbc-essiv:sha256
            keysize: 256 bits
            device:  /dev/sde
            offset:  4096 sectors
            size:    258048 sectors
            mode:    read/write
          # dmsetup table --target crypt
          ...
          sde_crypt: 0 258048 crypt aes-cbc-essiv:sha256 0000000000000000000000000000000000000000000000000000000000000000 0 8:64 4096
      
      [1] Both cryptsetup and dmsetup report the offset as 4096 and the size/
      length as 258048.  128 MiB / (4096+258048) = 512 byte units, even on a
      4096 byte sector size device.
      
      Update debugging of LUKS to this:
      
          # ./gpartedbin
          ======================
          libparted : 2.4
          ======================
          DEBUG: /dev/sdb5: LUKS closed
          DEBUG: /dev/sdb6: LUKS open mapping /dev/mapper/sdb6_crypt, offset=2097152, length=534773760
          /dev/sde: unrecognised disk label
          DEBUG: /dev/sde: LUKS open mapping /dev/mapper/sde_crypt, offset=2097152, length=132120576
      
      Bug 760080 - Implement read-only LUKS support
      317e4440
    • Mike Fleetwood's avatar
      Add busy detection of LUKS mapping (#760080) · 070d734e
      Mike Fleetwood authored
      Provide a minimal implementation of a luks file system class which only
      does busy detection.
      
      NOTE:
      For now, read-only LUKS support, a LUKS partition will be busy when a
      dm-crypt mapping exists.  Later when read-write LUKS support is added
      GParted will need to look at the busy status of the encrypted file
      system within the open LUKS partition and map LUKS partition busy status
      to encryption being open or closed.
      
      Bug 760080 - Implement read-only LUKS support
      070d734e
    • Mike Fleetwood's avatar
      Add initial loading of LUKS mapping details (#760080) · b77a6be7
      Mike Fleetwood authored
      Load basic details of active Device-mapper encryption mappings from the
      kernel.  Use dmsetup active targets.
      
          # cryptsetup luksFormat /dev/sdb5
          # cryptsetup luksFormat /dev/sdb6
          # cryptsetup luksOpen /dev/sdb6 sdb6_crypt
          # ls -l /dev/mapper/sdb6_crypt /dev/dm-0
          lrwxrwxrwx. 1 root root 7 Nov 15 09:03 /dev/mapper/sdb6_crypt -> ../dm-0
          brw-rw----. 1 root disk 253, 0 Nov 15 09:03 /dev/dm-0
          # ls -l /dev/sdb6
          brw-rw----. 1 root disk 8, 22 Nov 15 09:02 /dev/sdb6
          # dmsetup table --target crypt
          sdb6_crypt: 0 1044480 crypt aes-cbc-essiv:sha256 0000000000000000000000000000000000000000000000000000000000000000 0 8:22 4096
      
      So far just load the mapping name and underlying block device reference
      (path or major, minor pair).
      
      Note that all supported kernels appear to report the underlying block
      device as major, minor pair in the dmsetup output.  Underlying block
      device paths are added to the cache when found during a search to avoid
      stat(2) call on subsequent searches for the same path.
      
      Prints debugging to show results, like this:
      
          # ./gpartedbin
          ======================
          libparted : 2.4
          ======================
          DEBUG: /dev/sdb5: LUKS closed
          DEBUG: /dev/sdb6: LUKS open mapping /dev/mapper/sdb6_crypt
      
      Bug 760080 - Implement read-only LUKS support
      b77a6be7
  11. 26 Jan, 2016 4 commits
    • Mike Fleetwood's avatar
      Remove unnecessary sector_size parameter from Get_New_Partition methods · 24fa5533
      Mike Fleetwood authored
      The sector_size parameter is unnecessary as the value can be retrieved
      from the sector size of the selected Partition object on which the
      create new, copy & paste or resize/move operation is being performed.
      
      For the create new and resize/move operations it is trivial as the
      existing unallocated or in use Partition object on which the operation
      is being perform already contains the correct sector size.  For the copy
      & paste operation, which can copy across disk devices of different
      sector sizes, we merely have to use the sector size of the existing
      selected (destination) Partition object rather than copied (source)
      Partition object.  Hence these relevant lines in the new code:
      
          Dialog_Partition_Copy::set_data(selected_partition, copied_partition)
              new_partition = copied_partition.clone();
              ...
              new_partition->sector_size = selected_partition.sector_size;
      24fa5533
    • Mike Fleetwood's avatar
      Stop relying on specific values of PED_PARTITION_* enum · 3b3d8e44
      Mike Fleetwood authored
      The expressions used in the call to Set() were comparing
      lp_partition->type to 0 for the type parameter and passing it as a bool
      for the inside_extended parameter.  Libparted lp_partition->type is
      actually an enumeration.  The code was only working because of the
      specific values assigned to the symbolic names, PED_PARTITION_NORMAL = 0
      and PED_PARTITION_EXTENDED is non-zero (true).
      
      Make the code use the symbolic names and not depend on the actual
      enumeration values, which should be considered changeable and private to
      libparted.
      3b3d8e44
    • Mike Fleetwood's avatar
      Add FILESYSTEM_MAP[FS_UNALLOCATED] entry · 7870a92b
      Mike Fleetwood authored
      When displaying an unallocated partition
      Win_GParted::set_valid_operations() calls GParted_Core::get_fs() with
      parameter FS_UNALLOCATED.
      
      Before this change, get_fs() would fail to find file system capabilities
      set for FS_UNALLOCATED and construct a not supported capabilities set
      and return that.
      
      Afterwards, find_supported_filesystems() creates a not supported
      capabilities set from the NULL pointer for FS_UNALLOCATED and adds this
      entry into the FILESYSTEMS vector.  Then get_fs() finds that not
      supported capabilities set for FS_UNALLOCATED in the FILESYSTEMS vector
      and returns that.
      
      This makes no functional difference.  It just seems right as other
      unsupported but used file system types have entries in FILESYSTEM_MAP.
      7870a92b
    • Mike Fleetwood's avatar
      Initialise all struct FS members · 1a4cefb9
      Mike Fleetwood authored
      The struct FS constructor initialised every member *except* filesystem
      and busy.  Then in *most* cases after declaring struct FS, assignments
      followed like this:
          FS fs;
          fs.filesystem = FS_BTRFS;
          fs.busy       = FS::GPARTED;
      But member busy wasn't always initialised.
      
      Add initialisation of members filesystem and busy to the struct FS
      constructor.  Specify optional parameter to the constructor to set the
      filesystem member, or when left off filesystem is initialised to
      FS_UNKNOWN.
      1a4cefb9