summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorEmmanuel Vadot <manu@FreeBSD.Org>2020-01-21 17:50:15 +0100
committerEmmanuel Vadot <manu@FreeBSD.org>2020-04-21 19:26:54 +0200
commit6818a50b1215081d6a7b7b710f504a6b182320c8 (patch)
tree7c6d6c0e9a3b2d678f471b747db1d1314bf0dc95
parentc55a1e564cf6c9d42ce250af11101b7fc7e88a4e (diff)
libdrm: drmGetDeviceNameFromFd: Add FreeBSD variant
Get the major/minor via fstat and after checking that this is a drm node construct the full device node name using devname. Note that we should be able to use fdevname to avoid calling fstat + devname but for some reason it doesn't work on drm node (probably due to how the device node are created in the linux compat code for drm on FreeBSD). Signed-off-by: Emmanuel Vadot <manu@FreeBSD.org> Reviewed-by: Eric Engestrom <eric@engestrom.ch> Reviewed-by: Emil Velikov <emil.velikov@collabora.com>
-rw-r--r--xf86drm.c24
1 files changed, 24 insertions, 0 deletions
diff --git a/xf86drm.c b/xf86drm.c
index 9644bd57..e6f6a890 100644
--- a/xf86drm.c
+++ b/xf86drm.c
@@ -117,6 +117,8 @@ struct drm_pciinfo {
static drmServerInfoPtr drm_server_info;
+static bool drmNodeIsDRM(int maj, int min);
+
drm_public void drmSetServerInfo(drmServerInfoPtr info)
{
drm_server_info = info;
@@ -2768,6 +2770,27 @@ drm_public int drmIsMaster(int fd)
drm_public char *drmGetDeviceNameFromFd(int fd)
{
+#ifdef __FreeBSD__
+ struct stat sbuf;
+ char dname[SPECNAMELEN];
+ char name[SPECNAMELEN];
+ int maj, min;
+
+ if (fstat(fd, &sbuf))
+ return NULL;
+
+ maj = major(sbuf.st_rdev);
+ min = minor(sbuf.st_rdev);
+
+ if (!drmNodeIsDRM(maj, min) || !S_ISCHR(sbuf.st_mode))
+ return NULL;
+
+ if (!devname_r(sbuf.st_rdev, S_IFCHR, dname, sizeof(dname)))
+ return NULL;
+
+ snprintf(name, sizeof(name), "/dev/%s", dname);
+ return strdup(name);
+#else
char name[128];
struct stat sbuf;
dev_t d;
@@ -2790,6 +2813,7 @@ drm_public char *drmGetDeviceNameFromFd(int fd)
return NULL;
return strdup(name);
+#endif
}
static bool drmNodeIsDRM(int maj, int min)