Re: [PATCH igt v4] lib: Attempt to load the module for a missing device

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



On Tue, Nov 14, 2017 at 09:33:51PM +0000, Chris Wilson wrote:
> If we asked to open a particular chipset and we find no matching device,
> try again after attempting to load its module. Previously we only did
> this for vgem, which is not automatically probed during boot, but if we
> want to leave the module unloaded we have to try harder when we need the
> device.
> 
> v2: DRIVER_* are already masks (and not shifts). Use a common
> driver_open for both /dev/dri/cardX and /dev/dri/renderDX.
> v3: Beware making local variables accidentally static scoped.
> v4: Beware multiple threads trying and failing to open a device
> 
> Signed-off-by: Chris Wilson <chris@xxxxxxxxxxxxxxxxxx>
> ---
>  lib/drmtest.c | 97 +++++++++++++++++++++++++++++++++++------------------------
>  1 file changed, 57 insertions(+), 40 deletions(-)
> 
> diff --git a/lib/drmtest.c b/lib/drmtest.c
> index e6bdbc35..37cabd58 100644
> --- a/lib/drmtest.c
> +++ b/lib/drmtest.c
> @@ -44,6 +44,7 @@
>  #include <sys/syscall.h>
>  #include <sys/utsname.h>
>  #include <termios.h>
> +#include <pthread.h>
>  
>  #include "drmtest.h"
>  #include "i915_drm.h"
> @@ -235,25 +236,19 @@ static int modprobe(const char *driver)
>  	return igt_kmod_load(driver, "");
>  }
>  
> -/**
> - * __drm_open_driver:
> - * @chipset: OR'd flags for each chipset to search, eg. #DRIVER_INTEL
> - *
> - * Open the first DRM device we can find, searching up to 16 device nodes
> - *
> - * Returns:
> - * An open DRM fd or -1 on error
> - */
> -int __drm_open_driver(int chipset)
> +static void modprobe_i915(const char *name)
>  {
> -	if (chipset & DRIVER_VGEM)
> -		modprobe("vgem");
> +	/* When loading i915, we also want to load snd-hda et al */
> +	igt_i915_driver_load(NULL);
> +}
>  
> +static int __open_device(const char *base, int offset, unsigned int chipset)
> +{
>  	for (int i = 0; i < 16; i++) {
>  		char name[80];
>  		int fd;
>  
> -		sprintf(name, "/dev/dri/card%u", i);
> +		sprintf(name, "%s%u", base, i + offset);
>  		fd = open(name, O_RDWR);
>  		if (fd == -1)
>  			continue;
> @@ -262,16 +257,13 @@ int __drm_open_driver(int chipset)
>  		    has_known_intel_chipset(fd))
>  			return fd;
>  
> -		if (chipset & DRIVER_VC4 &&
> -		    is_vc4_device(fd))
> +		if (chipset & DRIVER_VC4 && is_vc4_device(fd))
>  			return fd;
>  
> -		if (chipset & DRIVER_VGEM &&
> -		    is_vgem_device(fd))
> +		if (chipset & DRIVER_VGEM && is_vgem_device(fd))
>  			return fd;
>  
> -		if (chipset & DRIVER_VIRTIO &&
> -		    is_virtio_device(fd))
> +		if (chipset & DRIVER_VIRTIO && is_virtio_device(fd))
>  			return fd;
>  
>  		if (chipset & DRIVER_AMDGPU && is_amd_device(fd))
> @@ -287,33 +279,58 @@ int __drm_open_driver(int chipset)
>  	return -1;
>  }
>  
> -static int __drm_open_driver_render(int chipset)
> +static int __open_driver(const char *base, int offset, unsigned int chipset)
>  {
> -	char *name;
> -	int i, fd;
> -
> -	for (i = 128; i < (128 + 16); i++) {
> -		int ret;
> -
> -		ret = asprintf(&name, "/dev/dri/renderD%u", i);
> -		igt_assert(ret != -1);
> -
> -		fd = open(name, O_RDWR);
> -		free(name);
> +	static pthread_mutex_t mutex = PTHREAD_MUTEX_INITIALIZER;
> +	static const struct module {
> +		unsigned int bit;
> +		const char *module;
> +		void (*modprobe)(const char *name);
> +	} modules[] = {
> +		{ DRIVER_AMDGPU, "amdgpu" },
> +		{ DRIVER_INTEL, "i915", modprobe_i915 },
> +		{ DRIVER_VC4, "vc4" },
> +		{ DRIVER_VGEM, "vgem" },
> +		{ DRIVER_VIRTIO, "virtio-gpu" },
> +		{}
> +	};
> +	int fd;
>  
> -		if (fd == -1)
> -			continue;
> +	fd = __open_device(base, offset, chipset);
> +	if (fd != -1)
> +		return fd;
>  
> -		if (!is_i915_device(fd) || !has_known_intel_chipset(fd)) {
> -			close(fd);
> -			fd = -1;
> -			continue;
> +	pthread_mutex_lock(&mutex);
> +	for (const struct module *m = modules; m->module; m++) {
> +		if (chipset & m->bit) {
> +			if (m->modprobe)
> +				m->modprobe(m->module);
> +			else
> +				modprobe(m->module);
>  		}
> -
> -		return fd;
>  	}
> +	pthread_mutex_unlock(&mutex);
>  
> -	return fd;
> +	return __open_device(base, offset, chipset);
> +}
> +
> +/**
> + * __drm_open_driver:
> + * @chipset: OR'd flags for each chipset to search, eg. #DRIVER_INTEL
> + *
> + * Open the first DRM device we can find, searching up to 16 device nodes
> + *
> + * Returns:
> + * An open DRM fd or -1 on error
> + */
> +int __drm_open_driver(int chipset)
> +{
> +	return __open_driver("/dev/dri/card", 0, chipset);
> +}
> +
> +static int __drm_open_driver_render(int chipset)
> +{
> +	return __open_driver("/dev/dri/renerD", 128, chipset);

s/rener/render/


-- 
Petri Latvala
_______________________________________________
Intel-gfx mailing list
Intel-gfx@xxxxxxxxxxxxxxxxxxxxx
https://lists.freedesktop.org/mailman/listinfo/intel-gfx




[Index of Archives]     [Linux USB Devel]     [Linux Audio Users]     [Yosemite News]     [Linux Kernel]     [Linux SCSI]
  Powered by Linux