routing_loop
routing_loop

Reputation: 11

Advice with updating this code getting - error: initialization of 'void (*)(struct platform_device *)' from incompatible pointer type

Hi i've been trying to compile a software module against against latest linux kernels 6.12 and 6.13-rc*. it's for a module of musdk, i've found very limited support unfortunately.

I get this error when compiling the module.

  CC [M]  mv_pp_uio.o
mv_pp_uio.c:196:19: error: initialization of 'void (*)(struct platform_device *)' from incompatible pointer type 'int (*)(struct platform_device *)' [-Werror=incompatible-pointer-types]
  196 |         .remove = mv_pp_uio_remove,
      |                   ^~~~~~~~~~~~~~~~
mv_pp_uio.c:196:19: note: (near initialization for 'mv_pp_uio_driver.<anonymous>.remove')

Investigation seems like since linux kernel 6.11 these types of functions using "(struct platform_device *pdev)" that if they were a "static int" no longer compile. Several of the patches to similar issues, seem to suggest changing the function to a "static void".

Original code of offending functions.

static int mv_pp_uio_remove(struct platform_device *pdev)
{
        struct uio_pdrv_pp_info *uio_pdrv_pp = platform_get_drvdata(pdev);
        struct device *dev = &pdev->dev;

        if (!uio_pdrv_pp)
                return -EINVAL;

        if (uio_pdrv_pp->uio_num != -EIO) {
                for (int idx = 0; idx <= uio_pdrv_pp->uio_num; ++idx) {
                        devm_kfree(dev, (void *)uio_pdrv_pp->uio[idx].name);
                        uio_unregister_device(&uio_pdrv_pp->uio[idx]);
                }
        }
        platform_set_drvdata(pdev, NULL);

        return 0;
}


static struct platform_driver mv_pp_uio_driver = {
        .driver = {
                .owner          = THIS_MODULE,
                .name           = DRIVER_NAME,
                .of_match_table = mv_pp_of_match,
        },
        .probe  = mv_pp_uio_probe,
        .remove = mv_pp_uio_remove,
};

Fix other similar issues suggest changing e.g. in this case:

static int mv_pp_uio_remove(struct platform_device *pdev) {

to 

static void mv_pp_uio_remove(struct platform_device *pdev) {

and removing the returns.

If i hack it to change to "void" and remove the returns it does actually compile. However I'm not convinced it's the best fix especially because of the removal of "if (!uio_pdrv_pp) return -EINVAL;" statement i.e:

static void mv_pp_uio_remove(struct platform_device *pdev)
{
        struct uio_pdrv_pp_info *uio_pdrv_pp = platform_get_drvdata(pdev);
        struct device *dev = &pdev->dev;

        /*if (!uio_pdrv_pp)
                return -EINVAL;*/

        if (uio_pdrv_pp->uio_num != -EIO) {
                for (int idx = 0; idx <= uio_pdrv_pp->uio_num; ++idx) {
                        devm_kfree(dev, (void *)uio_pdrv_pp->uio[idx].name);
                        uio_unregister_device(&uio_pdrv_pp->uio[idx]);
                }
        }
        platform_set_drvdata(pdev, NULL);
        
        /*return 0*/

}

cross compiled using aarch64-linux-gnu-gcc (Debian 12.2.0-14) 12.2.0.

Software - musdk-marvell-SDK12.24.10. modules that fail with same bug. cma and pp2.

building against Linux kernel - 6.13-rc13 (repeatable on 6.12) - also cross compiled using aarch64-linux-gnu-gcc .

I can provide further details on the source file is required.

uio_pdrv_pp

is defined in an earlier function.

uio_pdrv_pp = devm_kzalloc(dev, sizeof(struct uio_pdrv_pp_info),
                                   GFP_KERNEL);

I'm i'm unsure if removing

if (!uio_pdrv_pp)
                return -EINVAL;

from the offending function will significant affects.

Any help and advice or a better way of doing it is greatly appreciated.

Kind regards

Upvotes: 1

Views: 48

Answers (0)

Related Questions