[parted-devel] [PATCH 1/6] libparted: refactor device-mapper partition sync code

Jim Meyering jim at meyering.net
Tue Oct 16 13:58:06 UTC 2012


Phillip Susi wrote:
> The device-mapper partition sync code was still using the remove all
> partitions, then add new partitions method.  Refactor to use the same
> algorithm as regular disks: try to remove all, and ignore any that could
> not be removed but have not changed.
> ---
>  NEWS                   |    2 +
>  libparted/arch/linux.c |  403 +++++++++++++++++++++---------------------------
>  tests/Makefile.am      |    1 +
>  tests/t6002-dm-busy.sh |   94 +++++++++++
>  4 files changed, 275 insertions(+), 225 deletions(-)
>  create mode 100644 tests/t6002-dm-busy.sh
>
> diff --git a/NEWS b/NEWS
> index 4c4716d..f182cce 100644
> --- a/NEWS
> +++ b/NEWS
> @@ -3,6 +3,8 @@ GNU parted NEWS                                    -*- outline -*-
>  * Noteworthy changes in release ?.? (????-??-??) [?]
>
>  ** Bug Fixes
> +  libparted: Don't fail to manipulate partitions on dmraid disks that
> +  have other partitions in use.

Thanks for putting this together!
It's great to see both NEWS and a test addition.

...
> +static int
> +_dm_add_partition (PedDisk* disk, const PedPartition* part)
> +{
> +        LinuxSpecific*  arch_specific = LINUX_SPECIFIC (disk->dev);
> +
> +        /* Get map name from devicemapper */
> +        struct dm_task *task = dm_task_create (DM_DEVICE_INFO);
> +        if (!task)
> +                goto err;
> +
> +        if (!dm_task_set_major_minor (task, arch_specific->major,
> +                                      arch_specific->minor, 0))
> +                goto err;
> +
> +        if (!dm_task_run(task))
> +                goto err;
> +
> +        const char *dev_name = dm_task_get_name (task);
> +        char *vol_name;
> +        if (isdigit (dev_name[strlen (dev_name) - 1])) {
> +                if ( ! (vol_name = zasprintf ("%sp%d", dev_name, part->num)))
> +                        goto err;
> +        } else if ( ! (vol_name = zasprintf ("%s%d", dev_name, part->num)))
> +                goto err;

Please combine those:

           char *vol_name
             = zasprintf ("%s%s%d",
                          dev_name,
                          isdigit (dev_name[strlen (dev_name) - 1]) ? "p" : "",
                          part->num);
           if (vol_name == NULL)
                   goto err;

> +        /* Caution: dm_task_destroy frees dev_name.  */
> +        dm_task_destroy (task);
> +        task = NULL;
> +	char *params;

Please indent consistently.
s/TAB/        /
Yeah, I know it's hard, since the code does not use a consistent policy.

Eventually, when there seem to be few distro patches anywhere,
I'd like to convert all leading TABs to spaces.

> +        if ( ! (params = zasprintf ("%d:%d %lld", arch_specific->major,
> +                                    arch_specific->minor, part->geom.start)))
> +                goto err;
> +
> +        task = dm_task_create (DM_DEVICE_CREATE);
> +        if (!task)
> +                goto err;
> +
> +        dm_task_set_name (task, vol_name);
> +        dm_task_add_target (task, 0, part->geom.length,
> +                "linear", params);
> +        if (dm_task_run (task)) {
> +                dm_task_update_nodes();
> +                dm_task_destroy(task);
> +                free(params);
> +                free(vol_name);
> +                return 1;
> +        } else {
> +                _dm_remove_partition (disk, part->num);
> +        }
> +err:
> +        dm_task_update_nodes();
> +        if (task)
> +                dm_task_destroy (task);
> +        free (params);
> +        free (vol_name);
> +        return 0;
> +}
> +#endif

Please make a point always to configure with --enable-gcc-warnings.
When I applied your patch and built, it highlights these two problems:

      CC       arch/linux.lo
    arch/linux.c: In function '_dm_add_partition':
    arch/linux.c:2686:14: error: 'params' may be used uninitialized in this function [-Werror=maybe-uninitialized]
             free (params);
                  ^
    arch/linux.c:2687:14: error: 'vol_name' may be used uninitialized in this function [-Werror=maybe-uninitialized]
             free (vol_name);
                  ^
    cc1: all warnings being treated as errors
    make[3]: *** [arch/linux.lo] Error 1

i.e., hitting any of the "goto err" statements before "params" is set
would make libparted apply free to at least one uninitialized pointer.

Also, there was a trailing space on one of the added lines,
if you could remove it for a v2, that'd save me the trouble.

I'll have to defer reviewing the rest to later today or tomorrow,
but wanted to give you some feedback: partial now is better than full later.



More information about the parted-devel mailing list