When working with dumb buffers, DRM_IOCTL_MODE_MAP_DUMB and mmap works fine on Intel, but the mmap call fails on Radeon, Nouveau, and VMWGFX. I you look at the source for the xorg moderating driver, it only uses the dumb buffer IOCTL (i.e. it’s not using LibKMS), and if you look at the kernel source code for the dumb buffer IOCTLs for each of the Radeon, Nouveau, and VMWGFX drivers, they all implement the functions. Furthermore all of the IOCTLs succeed without error. Its only when you attempt to map the memory, that you get an error of “Invalid Argument”. Here is my map call:
mmap(0, size, PROT_READ | PROT_WRITE, MAP_SHARED, fd, map_arg.offset)
Is this a bug, or is there a different way to map the dumb buffers for these drivers other than LibKMS.
Thanks, - Rian
I did another test using the following that David put up on github:
https://github.com/dvdhrm/docs/blob/master/drm-howto/modeset.c
This test also fails on everything except Intel. What's really strange is this test actually does a test to verify that dumb buffers are supported, and the test passes in all cases. David's code is returning with the same error of "Invalid Argument" on the mmap call. Why would the other driver's claim to support dumb buffers, but have no means to map the memory?
- Rian
On Mon, Nov 10, 2014 at 2:48 PM, Rian Quinn rianquinn@gmail.com wrote:
When working with dumb buffers, DRM_IOCTL_MODE_MAP_DUMB and mmap works fine on Intel, but the mmap call fails on Radeon, Nouveau, and VMWGFX. I you look at the source for the xorg moderating driver, it only uses the dumb buffer IOCTL (i.e. it’s not using LibKMS), and if you look at the kernel source code for the dumb buffer IOCTLs for each of the Radeon, Nouveau, and VMWGFX drivers, they all implement the functions. Furthermore all of the IOCTLs succeed without error. Its only when you attempt to map the memory, that you get an error of “Invalid Argument”. Here is my map call:
mmap(0, size, PROT_READ | PROT_WRITE, MAP_SHARED, fd, map_arg.offset)
Is this a bug, or is there a different way to map the dumb buffers for these drivers other than LibKMS.
Thanks,
- Rian
On 11 November 2014 06:33, Rian Quinn rianquinn@gmail.com wrote:
I did another test using the following that David put up on github:
https://github.com/dvdhrm/docs/blob/master/drm-howto/modeset.c
This test also fails on everything except Intel. What's really strange is this test actually does a test to verify that dumb buffers are supported, and the test passes in all cases. David's code is returning with the same error of "Invalid Argument" on the mmap call. Why would the other driver's claim to support dumb buffers, but have no means to map the memory?
Just a guess, the size argument is wrong.
But you know you have the kernel source, stick some printks in the EINVAL return paths already.
Dave.
- Rian
On Mon, Nov 10, 2014 at 2:48 PM, Rian Quinn rianquinn@gmail.com wrote:
When working with dumb buffers, DRM_IOCTL_MODE_MAP_DUMB and mmap works fine on Intel, but the mmap call fails on Radeon, Nouveau, and VMWGFX. I you look at the source for the xorg moderating driver, it only uses the dumb buffer IOCTL (i.e. it’s not using LibKMS), and if you look at the kernel source code for the dumb buffer IOCTLs for each of the Radeon, Nouveau, and VMWGFX drivers, they all implement the functions. Furthermore all of the IOCTLs succeed without error. Its only when you attempt to map the memory, that you get an error of “Invalid Argument”. Here is my map call:
mmap(0, size, PROT_READ | PROT_WRITE, MAP_SHARED, fd, map_arg.offset)
Is this a bug, or is there a different way to map the dumb buffers for these drivers other than LibKMS.
Thanks,
- Rian
dri-devel mailing list dri-devel@lists.freedesktop.org http://lists.freedesktop.org/mailman/listinfo/dri-devel
I would be surprised if the size argument was the issue. That comes right out out of the create IOCTL unmodified. Here is the full source that I am using.
// Clear the arg buffers. memset(&create_arg, 0, sizeof(create_arg)); memset(&map_arg, 0, sizeof(map_arg));
// ------------------------------------------------------------------------ // Allocate
// Fill in the arguments for the IOCTL. Note that we only support 32bpp // dumb buffers so that is hard coded here. create_arg.width = width; create_arg.height = height; create_arg.bpp = 32;
// Allocate the dumb buffer if (drmIoctl(gpu->fd(), DRM_IOCTL_MODE_CREATE_DUMB, &create_arg)) { svWarning(0) << "Failed: DRM_IOCTL_MODE_CREATE_DUMB - " << strerror(errno); return; }
// Store the dumb buffer properties. mSize = create_arg.size; mStride = create_arg.pitch; mHandle = create_arg.handle;
// ------------------------------------------------------------------------ // Map
// Fill in the arguments for the IOCTL. map_arg.handle = mHandle;
// Allocate the dumb buffer if (drmIoctl(gpu->fd(), DRM_IOCTL_MODE_MAP_DUMB, &map_arg)) { svWarning(0) << "Failed: DRM_IOCTL_MODE_MAP_DUMB - " << strerror(errno); return; }
// Store the mapped memory if ((mVaddr = (svuint32 *)mmap(0, mSize, PROT_READ | PROT_WRITE, MAP_SHARED, gpu->fd(), map_arg.offset)) == MAP_FAILED) { // Need to clear out the address so that we don't try to use it. mVaddr = NULL;
// Error out. svWarning(0) << "Failed: Dumb Buffer mmap - " << strerror(errno); return; }
When this code runs, I get the "Invalid Argument" on the mmap.
On Mon, Nov 10, 2014 at 4:14 PM, Dave Airlie airlied@gmail.com wrote:
On 11 November 2014 06:33, Rian Quinn rianquinn@gmail.com wrote:
I did another test using the following that David put up on github:
https://github.com/dvdhrm/docs/blob/master/drm-howto/modeset.c
This test also fails on everything except Intel. What's really strange is this test actually does a test to verify that dumb buffers are supported, and the test passes in all cases. David's code is returning with the same error of "Invalid Argument" on the mmap call. Why would the other
driver's
claim to support dumb buffers, but have no means to map the memory?
Just a guess, the size argument is wrong.
But you know you have the kernel source, stick some printks in the EINVAL return paths already.
Dave.
- Rian
On Mon, Nov 10, 2014 at 2:48 PM, Rian Quinn rianquinn@gmail.com wrote:
When working with dumb buffers, DRM_IOCTL_MODE_MAP_DUMB and mmap works fine on Intel, but the mmap call fails on Radeon, Nouveau, and VMWGFX.
I you
look at the source for the xorg moderating driver, it only uses the dumb buffer IOCTL (i.e. it’s not using LibKMS), and if you look at the kernel source code for the dumb buffer IOCTLs for each of the Radeon, Nouveau,
and
VMWGFX drivers, they all implement the functions. Furthermore all of the IOCTLs succeed without error. Its only when you attempt to map the
memory,
that you get an error of “Invalid Argument”. Here is my map call:
mmap(0, size, PROT_READ | PROT_WRITE, MAP_SHARED, fd, map_arg.offset)
Is this a bug, or is there a different way to map the dumb buffers for these drivers other than LibKMS.
Thanks,
- Rian
dri-devel mailing list dri-devel@lists.freedesktop.org http://lists.freedesktop.org/mailman/listinfo/dri-devel
On 11 November 2014 07:33, Rian Quinn rianquinn@gmail.com wrote:
I would be surprised if the size argument was the issue. That comes right out out of the create IOCTL unmodified. Here is the full source that I am using.
// Clear the arg buffers. memset(&create_arg, 0, sizeof(create_arg)); memset(&map_arg, 0, sizeof(map_arg)); //
// Allocate // Fill in the arguments for the IOCTL. Note that we only support 32bpp // dumb buffers so that is hard coded here. create_arg.width = width; create_arg.height = height; create_arg.bpp = 32; // Allocate the dumb buffer if (drmIoctl(gpu->fd(), DRM_IOCTL_MODE_CREATE_DUMB, &create_arg)) { svWarning(0) << "Failed: DRM_IOCTL_MODE_CREATE_DUMB - " <<
strerror(errno); return; }
// Store the dumb buffer properties. mSize = create_arg.size; mStride = create_arg.pitch; mHandle = create_arg.handle; //
// Map // Fill in the arguments for the IOCTL. map_arg.handle = mHandle; // Allocate the dumb buffer if (drmIoctl(gpu->fd(), DRM_IOCTL_MODE_MAP_DUMB, &map_arg)) { svWarning(0) << "Failed: DRM_IOCTL_MODE_MAP_DUMB - " <<
strerror(errno); return; }
// Store the mapped memory if ((mVaddr = (svuint32 *)mmap(0, mSize, PROT_READ | PROT_WRITE,
MAP_SHARED, gpu->fd(), map_arg.offset)) == MAP_FAILED) { // Need to clear out the address so that we don't try to use it. mVaddr = NULL;
// Error out. svWarning(0) << "Failed: Dumb Buffer mmap - " << strerror(errno); return; }
mmap is probably truncating the offset,
look into, #define _FILE_OFFSET_BITS 64
AC_SYS_LARGEFILE
Dave.
Your a life savor man. That did the trick. I cannot test on the Radeon and Nouveau until I get back into the office tomorrow, but it worked great on the VMWGFX driver.
I'll also email David to let him know as his examples (which a lot of people reference) also need to that #define.
Thanks again, - Rian
On Mon, Nov 10, 2014 at 5:33 PM, Dave Airlie airlied@gmail.com wrote:
On 11 November 2014 07:33, Rian Quinn rianquinn@gmail.com wrote:
I would be surprised if the size argument was the issue. That comes right out out of the create IOCTL unmodified. Here is the full source that I am using.
// Clear the arg buffers. memset(&create_arg, 0, sizeof(create_arg)); memset(&map_arg, 0, sizeof(map_arg)); //
// Allocate // Fill in the arguments for the IOCTL. Note that we only support
32bpp
// dumb buffers so that is hard coded here. create_arg.width = width; create_arg.height = height; create_arg.bpp = 32; // Allocate the dumb buffer if (drmIoctl(gpu->fd(), DRM_IOCTL_MODE_CREATE_DUMB, &create_arg)) { svWarning(0) << "Failed: DRM_IOCTL_MODE_CREATE_DUMB - " <<
strerror(errno); return; }
// Store the dumb buffer properties. mSize = create_arg.size; mStride = create_arg.pitch; mHandle = create_arg.handle; //
// Map // Fill in the arguments for the IOCTL. map_arg.handle = mHandle; // Allocate the dumb buffer if (drmIoctl(gpu->fd(), DRM_IOCTL_MODE_MAP_DUMB, &map_arg)) { svWarning(0) << "Failed: DRM_IOCTL_MODE_MAP_DUMB - " <<
strerror(errno); return; }
// Store the mapped memory if ((mVaddr = (svuint32 *)mmap(0, mSize, PROT_READ | PROT_WRITE,
MAP_SHARED, gpu->fd(), map_arg.offset)) == MAP_FAILED) { // Need to clear out the address so that we don't try to use it. mVaddr = NULL;
// Error out. svWarning(0) << "Failed: Dumb Buffer mmap - " << strerror(errno); return; }
mmap is probably truncating the offset,
look into, #define _FILE_OFFSET_BITS 64
AC_SYS_LARGEFILE
Dave.
Verified that this fixed the issue for all of the video cards.
On Mon, Nov 10, 2014 at 5:38 PM, Rian Quinn rianquinn@gmail.com wrote:
Your a life savor man. That did the trick. I cannot test on the Radeon and Nouveau until I get back into the office tomorrow, but it worked great on the VMWGFX driver.
I'll also email David to let him know as his examples (which a lot of people reference) also need to that #define.
Thanks again,
- Rian
On Mon, Nov 10, 2014 at 5:33 PM, Dave Airlie airlied@gmail.com wrote:
On 11 November 2014 07:33, Rian Quinn rianquinn@gmail.com wrote:
I would be surprised if the size argument was the issue. That comes
right
out out of the create IOCTL unmodified. Here is the full source that I
am
using.
// Clear the arg buffers. memset(&create_arg, 0, sizeof(create_arg)); memset(&map_arg, 0, sizeof(map_arg)); //
// Allocate // Fill in the arguments for the IOCTL. Note that we only support
32bpp
// dumb buffers so that is hard coded here. create_arg.width = width; create_arg.height = height; create_arg.bpp = 32; // Allocate the dumb buffer if (drmIoctl(gpu->fd(), DRM_IOCTL_MODE_CREATE_DUMB, &create_arg)) { svWarning(0) << "Failed: DRM_IOCTL_MODE_CREATE_DUMB - " <<
strerror(errno); return; }
// Store the dumb buffer properties. mSize = create_arg.size; mStride = create_arg.pitch; mHandle = create_arg.handle; //
// Map // Fill in the arguments for the IOCTL. map_arg.handle = mHandle; // Allocate the dumb buffer if (drmIoctl(gpu->fd(), DRM_IOCTL_MODE_MAP_DUMB, &map_arg)) { svWarning(0) << "Failed: DRM_IOCTL_MODE_MAP_DUMB - " <<
strerror(errno); return; }
// Store the mapped memory if ((mVaddr = (svuint32 *)mmap(0, mSize, PROT_READ | PROT_WRITE,
MAP_SHARED, gpu->fd(), map_arg.offset)) == MAP_FAILED) { // Need to clear out the address so that we don't try to use it. mVaddr = NULL;
// Error out. svWarning(0) << "Failed: Dumb Buffer mmap - " <<
strerror(errno);
return; }
mmap is probably truncating the offset,
look into, #define _FILE_OFFSET_BITS 64
AC_SYS_LARGEFILE
Dave.
dri-devel@lists.freedesktop.org