Commit 4d18975c authored by Michał Mirosław's avatar Michał Mirosław Committed by Daniel Vetter
Browse files

fbdev: add remove_conflicting_pci_framebuffers()



Almost all PCI drivers using remove_conflicting_framebuffers() wrap it
with the same code.

v2: add kerneldoc for DRM helper
v3: propagate remove_conflicting_framebuffers() return value
  + move kerneldoc to where function is implemented

Signed-off-by: default avatarMichał Mirosław <mirq-linux@rere.qmqm.pl>
Acked-by: default avatarBartlomiej Zolnierkiewicz <b.zolnierkie@samsung.com>
Signed-off-by: default avatarDaniel Vetter <daniel.vetter@ffwll.ch>
Link: https://patchwork.freedesktop.org/patch/msgid/7db1c278276de420eb45a1b71d06b5eb6bbd49ef.1535810304.git.mirq-linux@rere.qmqm.pl
parent 69aa5355
Loading
Loading
Loading
Loading
+35 −0
Original line number Diff line number Diff line
@@ -34,6 +34,7 @@
#include <linux/fb.h>
#include <linux/fbcon.h>
#include <linux/mem_encrypt.h>
#include <linux/pci.h>

#include <asm/fb.h>

@@ -1830,6 +1831,40 @@ int remove_conflicting_framebuffers(struct apertures_struct *a,
}
EXPORT_SYMBOL(remove_conflicting_framebuffers);

/**
 * remove_conflicting_pci_framebuffers - remove firmware-configured framebuffers for PCI devices
 * @pdev: PCI device
 * @resource_id: index of PCI BAR configuring framebuffer memory
 * @name: requesting driver name
 *
 * This function removes framebuffer devices (eg. initialized by firmware)
 * using memory range configured for @pdev's BAR @resource_id.
 *
 * The function assumes that PCI device with shadowed ROM drives a primary
 * display and so kicks out vga16fb.
 */
int remove_conflicting_pci_framebuffers(struct pci_dev *pdev, int res_id, const char *name)
{
	struct apertures_struct *ap;
	bool primary = false;
	int err;

	ap = alloc_apertures(1);
	if (!ap)
		return -ENOMEM;

	ap->ranges[0].base = pci_resource_start(pdev, res_id);
	ap->ranges[0].size = pci_resource_len(pdev, res_id);
#ifdef CONFIG_X86
	primary = pdev->resource[PCI_ROM_RESOURCE].flags &
					IORESOURCE_ROM_SHADOW;
#endif
	err = remove_conflicting_framebuffers(ap, name, primary);
	kfree(ap);
	return err;
}
EXPORT_SYMBOL(remove_conflicting_pci_framebuffers);

/**
 *	register_framebuffer - registers a frame buffer device
 *	@fb_info: frame buffer info structure
+12 −0
Original line number Diff line number Diff line
@@ -615,4 +615,16 @@ drm_fb_helper_remove_conflicting_framebuffers(struct apertures_struct *a,
#endif
}

static inline int
drm_fb_helper_remove_conflicting_pci_framebuffers(struct pci_dev *pdev,
						  int resource_id,
						  const char *name)
{
#if IS_REACHABLE(CONFIG_FB)
	return remove_conflicting_pci_framebuffers(pdev, resource_id, name);
#else
	return 0;
#endif
}

#endif
+2 −0
Original line number Diff line number Diff line
@@ -632,6 +632,8 @@ extern ssize_t fb_sys_write(struct fb_info *info, const char __user *buf,
extern int register_framebuffer(struct fb_info *fb_info);
extern int unregister_framebuffer(struct fb_info *fb_info);
extern int unlink_framebuffer(struct fb_info *fb_info);
extern int remove_conflicting_pci_framebuffers(struct pci_dev *pdev, int res_id,
					       const char *name);
extern int remove_conflicting_framebuffers(struct apertures_struct *a,
					   const char *name, bool primary);
extern int fb_prepare_logo(struct fb_info *fb_info, int rotate);