Broken kernel build

Hello,

I am using the Terasic DE10-Standard development board and Quartus II 18.1 Standard
to develop an embedded system based on the Cyclone V and the DE10-Standard_LXDE version of
the Linux system provided by Terasic. I cloned the sources for u-boot and the kernel from
https://github.com/terasic/…

I have a broken kernel build. As of 9/25/2019 I was able to build the kernel without errors.
As of today, 10/28/2020 I encounter the following errors:

CHK include/config/kernel.release
CHK include/generated/uapi/linux/version.h
CHK include/generated/utsrelease.h
make[1]: include/generated/mach-types.h' is up to date. CHK include/generated/bounds.h CHK include/generated/timeconst.h CHK include/generated/asm-offsets.h CALL scripts/checksyscalls.sh CHK include/generated/compile.h CHK kernel/config_data.h CC drivers/video/fbdev/altvipfb2-plat.o LD drivers/video/fbdev/altvipfb2_drv.o LD drivers/video/fbdev/built-in.o drivers/video/fbdev/altvipfb2_drv.o:(___ksymtab_gpl+altvipfb2_probe+0x0): multiple definition of __ksymtab_altvipfb2_probe’
drivers/video/fbdev/altvipfb2.o:(___ksymtab_gpl+altvipfb2_probe+0x0): first defined here
drivers/video/fbdev/altvipfb2_drv.o: In function altvipfb2_plat_remove': /home/bmartinez/JT/linux/terasic/linux-socfpga/drivers/video/fbdev/altvipfb2-plat.c:122: multiple definition of __ksymtab_altvipfb2_remove’
drivers/video/fbdev/altvipfb2.o:/home/bmartinez/JT/linux/terasic/linux-socfpga/drivers/video/fbdev/altvipfb2.c:136: first defined here
drivers/video/fbdev/altvipfb2_drv.o: In function altvipfb2_probe': /home/bmartinez/JT/linux/terasic/linux-socfpga/drivers/video/fbdev/altvipfb2.c:136: multiple definition of altvipfb2_probe’
drivers/video/fbdev/altvipfb2.o:/home/bmartinez/JT/linux/terasic/linux-socfpga/drivers/video/fbdev/altvipfb2.c:136: first defined here
drivers/video/fbdev/altvipfb2_drv.o: In function altvipfb2_remove': /home/bmartinez/JT/linux/terasic/linux-socfpga/drivers/video/fbdev/altvipfb2.c:178: multiple definition of altvipfb2_remove’
drivers/video/fbdev/altvipfb2.o:/home/bmartinez/JT/linux/terasic/linux-socfpga/drivers/video/fbdev/altvipfb2.c:178: first defined here
make[3]: *** [drivers/video/fbdev/built-in.o] Error 1
make[2]: *** [drivers/video/fbdev] Error 2
make[1]: *** [drivers/video] Error 2
make: *** [drivers] Error 2

I am cross compiling using gcc-linaro-6.5.0-2018.12-x86_64_arm-linux-gnueabihf/bin/arm-linux-gnueabihf.
I am using ubuntu 16.04 LTS in a virtualbox VM.

Here are the relevant statements in the drivers/video/fbdev/Makefile

obj-$(CONFIG_FB_ALTERA_VIP_FB2) += altvipfb2.o
obj-$(CONFIG_FB_ALTERA_VIP_FB2_PLAT) += altvipfb2_drv.o
altvipfb2_drv-objs := altvipfb2-plat.o altvipfb2.o

Here are the function declarations in altvipfb2.h, which is included in both source modules:
int altvipfb2_probe(struct device *dev, void __iomem *base);
int altvipfb2_remove(struct device *dev);

I added extern to the above declarations, but this change did not fix the problem.

Here is the relevant code snippets from altvipfb2.c:

int altvipfb2_probe(struct device *dev, void __iomem *base)
{
int retval;
void *fbmem_virt;
struct altvipfb2_priv *fbpriv = dev_get_drvdata(dev);

fbmem_virt = dma_alloc_coherent(NULL,
				fbpriv->info.fix.smem_len,
				(void *)&fbpriv->info.fix.smem_start,
				GFP_KERNEL);
if (!fbmem_virt) {
	dev_err(dev,
		"altvipfb2: unable to allocate %d Bytes fb memory\n",
		fbpriv->info.fix.smem_len);
	return -ENOMEM;
}

fbpriv->info.screen_base = (char *)fbmem_virt;

retval = fb_alloc_cmap(&fbpriv->info.cmap, PALETTE_SIZE, 0);
if (retval < 0)
	goto err_dma_free;

altvipfb2_setup_fb_info(fbpriv);

altvipfb2_start_hw(base, &fbpriv->info);

dev_info(dev, "fb%d: %s frame buffer device at 0x%x+0x%x\n",
	 fbpriv->info.node, fbpriv->info.fix.id,
	 (unsigned int)fbpriv->info.fix.smem_start,
	 fbpriv->info.fix.smem_len);

return register_framebuffer(&fbpriv->info);

err_dma_free:
fb_dealloc_cmap(&fbpriv->info.cmap);
dma_free_coherent(NULL, fbpriv->info.fix.smem_len, fbmem_virt,
fbpriv->info.fix.smem_start);
return retval;
}
EXPORT_SYMBOL_GPL(altvipfb2_probe);

int altvipfb2_remove(struct device *dev)
{
struct altvipfb2_priv *fbpriv = dev_get_drvdata(dev);

altvipfb2_disable_hw(fbpriv->base);
dma_free_coherent(NULL, fbpriv->info.fix.smem_len,
		(void *)&fbpriv->info.screen_base,
		fbpriv->info.fix.smem_start);

return unregister_framebuffer(&fbpriv->info);

}
EXPORT_SYMBOL_GPL(altvipfb2_remove);

Here are the affected code snippets from altvipfb2-plat.c:
static int altvipfb2_plat_probe(struct platform_device *pdev)
{
int retval;

struct device *dev = &pdev->dev;
struct resource *reg_res;
struct altvipfb2_priv *fbdev;

fbdev = devm_kzalloc(dev, sizeof(*fbdev), GFP_KERNEL);
if (!fbdev)
	return -ENOMEM;

reg_res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
if (!reg_res)
	return -ENODEV;

fbdev->base = devm_ioremap_resource(dev, reg_res);
if (IS_ERR(fbdev->base)) {
	dev_err(dev, "devm_ioremap_resource failed\n");
	retval = PTR_ERR(fbdev->base);
	return -ENOMEM;
}

altvipfb2_of_setup(fbdev, pdev);

platform_set_drvdata(pdev, fbdev);

return altvipfb2_probe(dev, fbdev->base);

}

static int altvipfb2_plat_remove(struct platform_device *pdev)
{
return altvipfb2_remove(&pdev->dev);
}

Please let me know of any changes that may have occurred since last year.

Thanks,

Ben Martinez

I resolved this issue. Evidently the parsing logic for make changed from last year. The old Makefile had the following for the VFB drivers:
obj-$(CONFIG_FB_ALTERA_VIP_FB2) += altvipfb2.o
obj-$(CONFIG_FB_ALTERA_VIP_FB2_PLAT) += altvipfb2_drv.o
altvipfb2_drv-objs := altvipfb2-plat.o altvipfb2.o
This was producing the multiple symbol error. I changed the platform driver statement to this:
obj-$(CONFIG_FB_ALTERA_VIP_FB2_PLAT) += altvipfb2-plat.o altvipfb2.o
This change fixed the problem.