libdrm: Changes to 'ubuntu'
debian/changelog | 23
debian/control | 30
debian/libdrm-nouveau1.install | 1
debian/libdrm-nouveau1.symbols | 50
debian/patches/02_add_libdrm-nouveau.patch |11470 ++++++++++++++++++++++++++++
debian/patches/03_fix_unfreed_buffers.patch | 64
debian/patches/series | 3
debian/rules | 2
8 files changed, 11635 insertions(+), 8 deletions(-)
New commits:
commit ee5f7cb7a175c0ec32599bae7942ccc90bb306ab
Author: Christopher James Halse Rogers <chris@CowboyLaputopu.(none)>
Date: Wed Feb 11 21:20:35 2009 +1100
Add populated symbols file
diff --git a/debian/changelog b/debian/changelog
index 9a5f80c..8943b71 100644
--- a/debian/changelog
+++ b/debian/changelog
@@ -11,7 +11,10 @@ libdrm (2.4.4-0ubuntu7) UNRELEASED; urgency=low
Required for libdrm-nouveau.
* debian/rules:
* debian/control:
+ * debian/libdrm-nouveau1.install
+ Add libdrm-nouveau1 and libdrm-nouveau1-dbg package
+ * debian/libdrm-nouveau1.symbols:
+ + Add initial symbols file.
* debian/control:
+ Remove scary 'built from DRM snapshot' warning from long description of
libdrm-intel1{,-dbg}
diff --git a/debian/libdrm-nouveau1.symbols b/debian/libdrm-nouveau1.symbols
new file mode 100644
index 0000000..775e5ed
--- /dev/null
+++ b/debian/libdrm-nouveau1.symbols
@@ -0,0 +1,50 @@
+libdrm_nouveau.so.1 libdrm2 #MINVER#
+ dma@Base 2.4.4
+ nouveau_bo_busy@Base 2.4.4
+ nouveau_bo_emit_buffer@Base 2.4.4
+ nouveau_bo_fake@Base 2.4.4
+ nouveau_bo_handle_get@Base 2.4.4
+ nouveau_bo_handle_ref@Base 2.4.4
+ nouveau_bo_init@Base 2.4.4
+ nouveau_bo_map@Base 2.4.4
+ nouveau_bo_new@Base 2.4.4
+ nouveau_bo_pin@Base 2.4.4
+ nouveau_bo_ref@Base 2.4.4
+ nouveau_bo_takedown@Base 2.4.4
+ nouveau_bo_tile@Base 2.4.4
+ nouveau_bo_unmap@Base 2.4.4
+ nouveau_bo_unpin@Base 2.4.4
+ nouveau_bo_user@Base 2.4.4
+ nouveau_bo_validate_nomm@Base 2.4.4
+ nouveau_channel_alloc@Base 2.4.4
+ nouveau_channel_free@Base 2.4.4
+ nouveau_device_close@Base 2.4.4
+ nouveau_device_get_param@Base 2.4.4
+ nouveau_device_open@Base 2.4.4
+ nouveau_device_open_existing@Base 2.4.4
+ nouveau_device_set_param@Base 2.4.4
+ nouveau_dma_channel_init@Base 2.4.4
+ nouveau_dma_kickoff@Base 2.4.4
+ nouveau_dma_wait@Base 2.4.4
+ nouveau_fence_emit@Base 2.4.4
+ nouveau_fence_flush@Base 2.4.4
+ nouveau_fence_new@Base 2.4.4
+ nouveau_fence_ref@Base 2.4.4
+ nouveau_fence_signal_cb@Base 2.4.4
+ nouveau_fence_wait@Base 2.4.4
+ nouveau_grobj_alloc@Base 2.4.4
+ nouveau_grobj_autobind@Base 2.4.4
+ nouveau_grobj_free@Base 2.4.4
+ nouveau_grobj_ref@Base 2.4.4
+ nouveau_notifier_alloc@Base 2.4.4
+ nouveau_notifier_free@Base 2.4.4
+ nouveau_notifier_reset@Base 2.4.4
+ nouveau_notifier_return_val@Base 2.4.4
+ nouveau_notifier_status@Base 2.4.4
+ nouveau_notifier_wait_status@Base 2.4.4
+ nouveau_pushbuf_emit_reloc@Base 2.4.4
+ nouveau_pushbuf_flush@Base 2.4.4
+ nouveau_pushbuf_init@Base 2.4.4
+ nouveau_resource_alloc@Base 2.4.4
+ nouveau_resource_free@Base 2.4.4
+ nouveau_resource_init@Base 2.4.4
commit 314569bf5bd2ab0b34d43b426248222eb25b7f16
Author: Christopher James Halse Rogers <chris@CowboyLaputopu.(none)>
Date: Wed Feb 11 18:56:20 2009 +1100
Add patch to update nouveau_drm.h to new patchlevel
diff --git a/debian/changelog b/debian/changelog
index 5e6fd78..9a5f80c 100644
--- a/debian/changelog
+++ b/debian/changelog
@@ -5,6 +5,10 @@ libdrm (2.4.4-0ubuntu7) UNRELEASED; urgency=low
+ Add commits from drm master adding a libdrm-nouveau library, and
include the latest fixes. This library is now required by the DDX
component.
+ * debian/patchs/04_update_nouveau_header
+ + Update the nouveau DRM header to the new patchlevel. Pulled from
+ upstream, with the non-userspace components removed from the patch.
+ Required for libdrm-nouveau.
* debian/rules:
* debian/control:
+ Add libdrm-nouveau1 and libdrm-nouveau1-dbg package
diff --git a/debian/patches/series b/debian/patches/series
index 660ce57..300de28 100644
--- a/debian/patches/series
+++ b/debian/patches/series
@@ -1,3 +1,4 @@
01_default_perms.diff
02_add_libdrm-nouveau.patch
03_fix_unfreed_buffers.patch
+04_update_nouveau_header.patch
commit 371b78f94d84d816a6b1877ac85bd34786328ee7
Author: Christopher James Halse Rogers <chris@CowboyLaputopu.(none)>
Date: Wed Feb 11 18:53:41 2009 +1100
Remove accidental 'expect this to be unstable' warning from long description of libdrm-intel
diff --git a/debian/changelog b/debian/changelog
index 894e567..5e6fd78 100644
--- a/debian/changelog
+++ b/debian/changelog
@@ -6,7 +6,11 @@ libdrm (2.4.4-0ubuntu7) UNRELEASED; urgency=low
include the latest fixes. This library is now required by the DDX
component.
* debian/rules:
- + Add libdrm-nouveau1 package
+ * debian/control:
+ + Add libdrm-nouveau1 and libdrm-nouveau1-dbg package
+ * debian/control:
+ + Remove scary 'built from DRM snapshot' warning from long description of
+ libdrm-intel1{,-dbg}
-- Christopher James Halse Rogers <raof@ubuntu.com> Wed, 11 Feb 2009 18:12:41 +1100
diff --git a/debian/control b/debian/control
index be710a1..b3a8d96 100644
--- a/debian/control
+++ b/debian/control
@@ -62,10 +62,6 @@ Description: Userspace interface to intel-specific kernel DRM services -- runtim
DRM services. DRM stands for "Direct Rendering Manager", which is the
kernelspace portion of the "Direct Rendering Infrastructure" (DRI). The DRI is
currently used on Linux to provide hardware-accelerated OpenGL drivers.
- .
- This package is built from a snapshot of DRM development code, to provide the
- features necessary for testing new X.org drivers. Do NOT expect this package
- to be stable!
Package: libdrm-intel1-dbg
Section: libdevel
@@ -78,10 +74,6 @@ Description: Userspace interface to intel-specific kernel DRM services -- debugg
of the "Direct Rendering Infrastructure" (DRI). The DRI is currently used on
Linux to provide hardware-accelerated OpenGL drivers.
.
- This package is built from a snapshot of DRM development code, to provide the
- features necessary for testing new X.org drivers. Do NOT expect this package
- to be stable!
- .
This package provides the debugging symbols for the libdrm-intel1 package.
Package: libdrm-nouveau1
commit 1e6d7d053eb08bba56abf7a6d8779f98ba703f3c
Author: Christopher James Halse Rogers <chris@CowboyLaputopu.(none)>
Date: Wed Feb 11 18:19:19 2009 +1100
Get git to actually commit the changes to debian/control.
Git is composed entirely of sharp edges
diff --git a/debian/changelog b/debian/changelog
index 3259562..894e567 100644
--- a/debian/changelog
+++ b/debian/changelog
@@ -1,4 +1,4 @@
-libdrm (2.4.4-0ubuntu7) jaunty; urgency=low
+libdrm (2.4.4-0ubuntu7) UNRELEASED; urgency=low
* debian/patches/02_add_libdrm-nouveau
* debian/patches/03_fix_unfreed_buffers
@@ -8,7 +8,7 @@ libdrm (2.4.4-0ubuntu7) jaunty; urgency=low
* debian/rules:
+ Add libdrm-nouveau1 package
- --
+ -- Christopher James Halse Rogers <raof@ubuntu.com> Wed, 11 Feb 2009 18:12:41 +1100
libdrm (2.4.4-0ubuntu6) jaunty; urgency=low
diff --git a/debian/control b/debian/control
index 508916c..be710a1 100644
--- a/debian/control
+++ b/debian/control
@@ -84,3 +84,25 @@ Description: Userspace interface to intel-specific kernel DRM services -- debugg
.
This package provides the debugging symbols for the libdrm-intel1 package.
+Package: libdrm-nouveau1
+Section: libs
+Architecture: any
+Depends: ${shlibs:Depends}, ${misc:Depends}
+Description: Userspace interface to intel-specific kernel DRM services -- runtime
+ This library implements the userspace interface to the intel-specific kernel
+ DRM services. DRM stands for "Direct Rendering Manager", which is the
+ kernelspace portion of the "Direct Rendering Infrastructure" (DRI). The DRI is
+ currently used on Linux to provide hardware-accelerated OpenGL drivers.
+
+Package: libdrm-nouveau1-dbg
+Section: libdevel
+Priority: extra
+Architecture: any
+Depends: libdrm-nouveau1 (= ${binary:Version}), ${misc:Depends}
+Description: Userspace interface to intel-specific kernel DRM services -- debugging symbols
+ This library implements the userspace interface to the kernel DRM services.
+ DRM stands for "Direct Rendering Manager", which is the kernelspace portion
+ of the "Direct Rendering Infrastructure" (DRI). The DRI is currently used on
+ Linux to provide hardware-accelerated OpenGL drivers.
+ .
+ This package provides the debugging symbols for the libdrm-nouveau1 package.
commit 21a4abef59cb763886e7c8af4237081e2560cd4e
Author: Christopher James Halse Rogers <chris@CowboyLaputopu.(none)>
Date: Wed Feb 11 18:17:18 2009 +1100
* debian/patches/02_add_libdrm-nouveau
* debian/patches/03_fix_unfreed_buffers
+ Add commits from drm master adding a libdrm-nouveau library, and
include the latest fixes. This library is now required by the DDX
component.
* debian/rules:
+ Add libdrm-nouveau1 package
diff --git a/debian/changelog b/debian/changelog
index ea8ec6f..3259562 100644
--- a/debian/changelog
+++ b/debian/changelog
@@ -1,3 +1,15 @@
+libdrm (2.4.4-0ubuntu7) jaunty; urgency=low
+
+ * debian/patches/02_add_libdrm-nouveau
+ * debian/patches/03_fix_unfreed_buffers
+ + Add commits from drm master adding a libdrm-nouveau library, and
+ include the latest fixes. This library is now required by the DDX
+ component.
+ * debian/rules:
+ + Add libdrm-nouveau1 package
+
+ --
+
libdrm (2.4.4-0ubuntu6) jaunty; urgency=low
* Bump dep on linux-libc-dev dep to >= 2.6.28-1.4 on lpia as this version of
diff --git a/debian/libdrm-nouveau1.install b/debian/libdrm-nouveau1.install
new file mode 100644
index 0000000..7650858
--- /dev/null
+++ b/debian/libdrm-nouveau1.install
@@ -0,0 +1 @@
+usr/lib/libdrm_nouveau.so.*
diff --git a/debian/patches/02_add_libdrm-nouveau.patch b/debian/patches/02_add_libdrm-nouveau.patch
new file mode 100644
index 0000000..c5c95c3
--- /dev/null
+++ b/debian/patches/02_add_libdrm-nouveau.patch
@@ -0,0 +1,11470 @@
+From 225e7e274f49d5e01fa1ad3fbbb9f1499865fe67 Mon Sep 17 00:00:00 2001
+From: Ben Skeggs <skeggsb@gmail.com>
+Date: Fri, 30 Jan 2009 01:25:35 +0000
+Subject: nouveau: install libdrm_nouveau with libdrm
+
+---
+diff --git a/configure.ac b/configure.ac
+index a65f79e..62d1a29 100644
+--- a/configure.ac
++++ b/configure.ac
+@@ -131,6 +131,8 @@ AC_OUTPUT([
+ Makefile
+ libdrm/Makefile
+ libdrm/intel/Makefile
++ libdrm/nouveau/Makefile
++ libdrm/nouveau/libdrm_nouveau.pc
+ shared-core/Makefile
+ tests/Makefile
+ tests/modeprint/Makefile
+diff --git a/libdrm/Makefile.am b/libdrm/Makefile.am
+index a568aac..cba4586 100644
+--- a/libdrm/Makefile.am
++++ b/libdrm/Makefile.am
+@@ -18,7 +18,7 @@
+ # IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+ # CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+-SUBDIRS = . intel
++SUBDIRS = . intel nouveau
+
+ libdrm_la_LTLIBRARIES = libdrm.la
+ libdrm_ladir = $(libdir)
+diff --git a/libdrm/nouveau/Makefile.am b/libdrm/nouveau/Makefile.am
+new file mode 100644
+index 0000000..80fb780
+--- a/libdrm/nouveau/Makefile.am
++++ b/libdrm/nouveau/Makefile.am
+@@ -0,0 +1,40 @@
++AM_CFLAGS = \
++ $(WARN_CFLAGS) \
++ -I$(top_srcdir)/libdrm \
++ -I$(top_srcdir)/libdrm/nouveau \
++ $(PTHREADSTUBS_CFLAGS) \
++ -I$(top_srcdir)/shared-core
++
++libdrm_nouveau_la_LTLIBRARIES = libdrm_nouveau.la
++libdrm_nouveau_ladir = $(libdir)
++libdrm_nouveau_la_LDFLAGS = -version-number 1:0:0 -no-undefined
++libdrm_nouveau_la_LIBADD = ../libdrm.la @PTHREADSTUBS_LIBS@
++
++libdrm_nouveau_la_SOURCES = \
++ nouveau_device.c \
++ nouveau_channel.c \
++ nouveau_pushbuf.c \
++ nouveau_grobj.c \
++ nouveau_notifier.c \
++ nouveau_bo.c \
++ nouveau_resource.c \
++ nouveau_dma.c \
++ nouveau_fence.c
++
++libdrm_nouveaucommonincludedir = ${includedir}/nouveau
++libdrm_nouveaucommoninclude_HEADERS = \
++ nouveau_device.h \
++ nouveau_channel.h \
++ nouveau_grobj.h \
++ nouveau_notifier.h \
++ nouveau_pushbuf.h \
++ nouveau_bo.h \
++ nouveau_resource.h \
++ nouveau_class.h
++
++libdrm_nouveauincludedir = ${includedir}/drm
++libdrm_nouveauinclude_HEADERS = \
++ nouveau_drmif.h
++
++pkgconfigdir = @pkgconfigdir@
++pkgconfig_DATA = libdrm_nouveau.pc
+diff --git a/libdrm/nouveau/libdrm_nouveau.pc.in b/libdrm/nouveau/libdrm_nouveau.pc.in
+new file mode 100644
+index 0000000..9e67a23
+--- a/libdrm/nouveau/libdrm_nouveau.pc.in
++++ b/libdrm/nouveau/libdrm_nouveau.pc.in
+@@ -0,0 +1,10 @@
++prefix=@prefix@
++exec_prefix=@exec_prefix@
++libdir=@libdir@
++includedir=@includedir@
++
++Name: libdrm_nouveau
++Description: Userspace interface to nouveau kernel DRM services
++Version: 0.5
++Libs: -L${libdir} -ldrm_nouveau
++Cflags: -I${includedir} -I${includedir}/drm -I${includedir}/nouveau
+diff --git a/libdrm/nouveau/nouveau_bo.c b/libdrm/nouveau/nouveau_bo.c
+new file mode 100644
+index 0000000..0ab426d
+--- a/libdrm/nouveau/nouveau_bo.c
++++ b/libdrm/nouveau/nouveau_bo.c
+@@ -0,0 +1,838 @@
++/*
++ * Copyright 2007 Nouveau Project
++ *
++ * Permission is hereby granted, free of charge, to any person obtaining a
++ * copy of this software and associated documentation files (the "Software"),
++ * to deal in the Software without restriction, including without limitation
++ * the rights to use, copy, modify, merge, publish, distribute, sublicense,
++ * and/or sell copies of the Software, and to permit persons to whom the
++ * Software is furnished to do so, subject to the following conditions:
++ *
++ * The above copyright notice and this permission notice shall be included in
++ * all copies or substantial portions of the Software.
++ *
++ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
++ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
++ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
++ * THE AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
++ * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF
++ * OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
++ * SOFTWARE.
++ */
++
++#include <stdint.h>
++#include <stdlib.h>
++#include <errno.h>
++#include <assert.h>
++
++#include <sys/mman.h>
++#include <sys/ioctl.h>
++
++#include "nouveau_private.h"
++
++int
++nouveau_bo_init(struct nouveau_device *dev)
++{
++ return 0;
++}
++
++void
++nouveau_bo_takedown(struct nouveau_device *dev)
++{
++}
++
++static int
++nouveau_bo_allocated(struct nouveau_bo_priv *nvbo)
++{
++ if (nvbo->sysmem || nvbo->handle || (nvbo->flags & NOUVEAU_BO_PIN))
++ return 1;
++ return 0;
++}
++
++static int
++nouveau_bo_ualloc(struct nouveau_bo_priv *nvbo)
++{
++ if (nvbo->user || nvbo->sysmem) {
++ assert(nvbo->sysmem);
++ return 0;
++ }
++
++ nvbo->sysmem = malloc(nvbo->size);
++ if (!nvbo->sysmem)
++ return -ENOMEM;
++
++ return 0;
++}
++
++static void
++nouveau_bo_ufree(struct nouveau_bo_priv *nvbo)
++{
++ if (nvbo->sysmem) {
++ if (!nvbo->user)
++ free(nvbo->sysmem);
++ nvbo->sysmem = NULL;
++ }
++}
++
++static void
++nouveau_bo_kfree_nomm(struct nouveau_bo_priv *nvbo)
++{
++ struct nouveau_device_priv *nvdev = nouveau_device(nvbo->base.device);
++ struct drm_nouveau_mem_free req;
++
++ if (nvbo->map) {
++ drmUnmap(nvbo->map, nvbo->size);
++ nvbo->map = NULL;
++ }
++
++ req.offset = nvbo->offset;
++ if (nvbo->domain & NOUVEAU_BO_GART)
++ req.flags = NOUVEAU_MEM_AGP | NOUVEAU_MEM_PCI;
++ else
++ if (nvbo->domain & NOUVEAU_BO_VRAM)
++ req.flags = NOUVEAU_MEM_FB;
++ drmCommandWrite(nvdev->fd, DRM_NOUVEAU_MEM_FREE, &req, sizeof(req));
++
++ nvbo->handle = 0;
++}
++
++static void
++nouveau_bo_kfree(struct nouveau_bo_priv *nvbo)
++{
++ struct nouveau_device_priv *nvdev = nouveau_device(nvbo->base.device);
++ struct drm_gem_close req;
++
++ if (!nvbo->handle)
++ return;
++
++ if (!nvdev->mm_enabled) {
++ nouveau_bo_kfree_nomm(nvbo);
++ return;
++ }
++
++ if (nvbo->map) {
++ munmap(nvbo->map, nvbo->size);
++ nvbo->map = NULL;
++ }
++
++ req.handle = nvbo->handle;
++ nvbo->handle = 0;
++ ioctl(nvdev->fd, DRM_IOCTL_GEM_CLOSE, &req);
++}
++
++static int
++nouveau_bo_kalloc_nomm(struct nouveau_bo_priv *nvbo)
++{
++ struct nouveau_device_priv *nvdev = nouveau_device(nvbo->base.device);
++ struct drm_nouveau_mem_alloc req;
++ int ret;
++
++ if (nvbo->handle)
++ return 0;
++
++ if (!(nvbo->flags & (NOUVEAU_BO_VRAM|NOUVEAU_BO_GART)))
++ nvbo->flags |= (NOUVEAU_BO_GART | NOUVEAU_BO_VRAM);
++
++ req.size = nvbo->size;
++ req.alignment = nvbo->align;
++ req.flags = 0;
++ if (nvbo->flags & NOUVEAU_BO_VRAM)
++ req.flags |= NOUVEAU_MEM_FB;
++ if (nvbo->flags & NOUVEAU_BO_GART)
++ req.flags |= (NOUVEAU_MEM_AGP | NOUVEAU_MEM_PCI);
++ if (nvbo->flags & NOUVEAU_BO_TILED) {
++ req.flags |= NOUVEAU_MEM_TILE;
++ if (nvbo->flags & NOUVEAU_BO_ZTILE)
++ req.flags |= NOUVEAU_MEM_TILE_ZETA;
++ }
++ req.flags |= NOUVEAU_MEM_MAPPED;
++
++ ret = drmCommandWriteRead(nvdev->fd, DRM_NOUVEAU_MEM_ALLOC,
++ &req, sizeof(req));
++ if (ret)
++ return ret;
++
++ nvbo->handle = req.map_handle;
++ nvbo->size = req.size;
++ nvbo->offset = req.offset;
++ if (req.flags & (NOUVEAU_MEM_AGP | NOUVEAU_MEM_PCI))
++ nvbo->domain = NOUVEAU_BO_GART;
++ else
++ if (req.flags & NOUVEAU_MEM_FB)
++ nvbo->domain = NOUVEAU_BO_VRAM;
++
++ return 0;
++}
++
++static int
++nouveau_bo_kalloc(struct nouveau_bo_priv *nvbo, struct nouveau_channel *chan)
++{
++ struct nouveau_device_priv *nvdev = nouveau_device(nvbo->base.device);
++ struct drm_nouveau_gem_new req;
++ int ret;
++
++ if (nvbo->handle || (nvbo->flags & NOUVEAU_BO_PIN))
++ return 0;
++
++ if (!nvdev->mm_enabled)
++ return nouveau_bo_kalloc_nomm(nvbo);
++
++ req.channel_hint = chan ? chan->id : 0;
++
++ req.size = nvbo->size;
++ req.align = nvbo->align;
++
++ req.domain = 0;
++
++ if (nvbo->flags & NOUVEAU_BO_VRAM)
++ req.domain |= NOUVEAU_GEM_DOMAIN_VRAM;
++
++ if (nvbo->flags & NOUVEAU_BO_GART)
++ req.domain |= NOUVEAU_GEM_DOMAIN_GART;
++
++ if (nvbo->flags & NOUVEAU_BO_TILED) {
++ req.domain |= NOUVEAU_GEM_DOMAIN_TILE;
++ if (nvbo->flags & NOUVEAU_BO_ZTILE)
++ req.domain |= NOUVEAU_GEM_DOMAIN_TILE_ZETA;
++ }
++
++ if (!req.domain) {
++ req.domain |= (NOUVEAU_GEM_DOMAIN_VRAM |
++ NOUVEAU_GEM_DOMAIN_GART);
++ }
++
++ ret = drmCommandWriteRead(nvdev->fd, DRM_NOUVEAU_GEM_NEW,
++ &req, sizeof(req));
++ if (ret)
++ return ret;
++ nvbo->handle = nvbo->base.handle = req.handle;
++ nvbo->size = req.size;
++ nvbo->domain = req.domain;
++ nvbo->offset = req.offset;
++
++ return 0;
++}
++
++static int
++nouveau_bo_kmap_nomm(struct nouveau_bo_priv *nvbo)
++{
++ struct nouveau_device_priv *nvdev = nouveau_device(nvbo->base.device);
++ int ret;
++
++ ret = drmMap(nvdev->fd, nvbo->handle, nvbo->size, &nvbo->map);
++ if (ret) {
++ nvbo->map = NULL;
++ return ret;
++ }
++
++ return 0;
++}
++
++static int
++nouveau_bo_kmap(struct nouveau_bo_priv *nvbo)
++{
++ struct nouveau_device_priv *nvdev = nouveau_device(nvbo->base.device);
++ struct drm_nouveau_gem_mmap req;
++ int ret;
++
++ if (nvbo->map)
++ return 0;
++
++ if (!nvbo->handle)
++ return -EINVAL;
++
++ if (!nvdev->mm_enabled)
++ return nouveau_bo_kmap_nomm(nvbo);
++
++ req.handle = nvbo->handle;
++ ret = drmCommandWriteRead(nvdev->fd, DRM_NOUVEAU_GEM_MMAP,
++ &req, sizeof(req));
++ if (ret)
++ return ret;
++
++ nvbo->map = (void *)(unsigned long)req.vaddr;
++ return 0;
++}
++
++int
++nouveau_bo_new(struct nouveau_device *dev, uint32_t flags, int align,
++ int size, struct nouveau_bo **bo)
++{
++ struct nouveau_bo_priv *nvbo;
++ int ret;
++
++ if (!dev || !bo || *bo)
++ return -EINVAL;
++
++ nvbo = calloc(1, sizeof(struct nouveau_bo_priv));
++ if (!nvbo)
++ return -ENOMEM;
++ nvbo->base.device = dev;
++ nvbo->base.size = size;
++
++ nvbo->refcount = 1;
++ /* Don't set NOUVEAU_BO_PIN here, or nouveau_bo_allocated() will
++ * decided the buffer's already allocated when it's not. The
++ * call to nouveau_bo_pin() later will set this flag.
++ */
++ nvbo->flags = (flags & ~NOUVEAU_BO_PIN);
++ nvbo->size = size;
++ nvbo->align = align;
++
++ /*XXX: murder me violently */
++ if (flags & NOUVEAU_BO_TILED) {
++ nvbo->base.tiled = 1;
++ if (flags & NOUVEAU_BO_ZTILE)
++ nvbo->base.tiled |= 2;
++ }
++
++ if (flags & NOUVEAU_BO_PIN) {
++ ret = nouveau_bo_pin((void *)nvbo, nvbo->flags);
++ if (ret) {
++ nouveau_bo_ref(NULL, (void *)nvbo);
++ return ret;
++ }
++ }
++
++ *bo = &nvbo->base;
++ return 0;
++}
++
++int
++nouveau_bo_user(struct nouveau_device *dev, void *ptr, int size,
++ struct nouveau_bo **bo)
++{
++ struct nouveau_bo_priv *nvbo;
++ int ret;
++
++ ret = nouveau_bo_new(dev, 0, 0, size, bo);
++ if (ret)
++ return ret;
++ nvbo = nouveau_bo(*bo);
++
++ nvbo->sysmem = ptr;
++ nvbo->user = 1;
++ return 0;
++}
++
++int
++nouveau_bo_fake(struct nouveau_device *dev, uint64_t offset, uint32_t flags,
++ uint32_t size, void *map, struct nouveau_bo **bo)
++{
++ struct nouveau_bo_priv *nvbo;
++ int ret;
++
++ ret = nouveau_bo_new(dev, flags & ~NOUVEAU_BO_PIN, 0, size, bo);
++ if (ret)
++ return ret;
++ nvbo = nouveau_bo(*bo);
++
++ nvbo->flags = flags | NOUVEAU_BO_PIN;
++ nvbo->domain = (flags & (NOUVEAU_BO_VRAM|NOUVEAU_BO_GART));
++ nvbo->offset = offset;
++ nvbo->size = nvbo->base.size = size;
++ nvbo->map = map;
++ nvbo->base.flags = nvbo->flags;
++ nvbo->base.offset = nvbo->offset;
++ return 0;
++}
++
++int
++nouveau_bo_handle_get(struct nouveau_bo *bo, uint32_t *handle)
++{
++ struct nouveau_device_priv *nvdev = nouveau_device(bo->device);
++ struct nouveau_bo_priv *nvbo = nouveau_bo(bo);
++ int ret;
++
++ if (!bo || !handle)
++ return -EINVAL;
++
++ if (!nvdev->mm_enabled)
++ return -ENODEV;
++
++ if (!nvbo->global_handle) {
++ struct drm_gem_flink req;
++
++ ret = nouveau_bo_kalloc(nvbo, NULL);
++ if (ret)
++ return ret;
++
++ req.handle = nvbo->handle;
++ ret = ioctl(nvdev->fd, DRM_IOCTL_GEM_FLINK, &req);
++ if (ret) {
++ nouveau_bo_kfree(nvbo);
++ return ret;
++ }
++
++ nvbo->global_handle = req.name;
++ }
++
++ *handle = nvbo->global_handle;
++ return 0;
++}
++
++int
++nouveau_bo_handle_ref(struct nouveau_device *dev, uint32_t handle,
++ struct nouveau_bo **bo)
++{
++ struct nouveau_device_priv *nvdev = nouveau_device(dev);
++ struct nouveau_bo_priv *nvbo;
++ struct drm_gem_open req;
++ int ret;
++
++ ret = nouveau_bo_new(dev, 0, 0, 0, bo);
++ if (ret)
++ return ret;
++ nvbo = nouveau_bo(*bo);
++
++ if (!nvdev->mm_enabled) {
++ nvbo->handle = 0;
++ nvbo->offset = handle;
++ nvbo->domain = NOUVEAU_BO_VRAM;
++ nvbo->flags = NOUVEAU_BO_VRAM | NOUVEAU_BO_PIN;
++ nvbo->base.offset = nvbo->offset;
++ nvbo->base.flags = nvbo->flags;
++ } else {
++ req.name = handle;
++ ret = ioctl(nvdev->fd, DRM_IOCTL_GEM_OPEN, &req);
++ if (ret) {
++ nouveau_bo_ref(NULL, bo);
++ return ret;
++ }
++
++ nvbo->size = req.size;
++ nvbo->handle = req.handle;
++ }
++
++ return 0;
++}
++
++static void
++nouveau_bo_del_cb(void *priv)
++{
++ struct nouveau_bo_priv *nvbo = priv;
++
++ nouveau_bo_kfree(nvbo);
++ free(nvbo);
++}
++
++static void
++nouveau_bo_del(struct nouveau_bo **bo)
++{
++ struct nouveau_bo_priv *nvbo;
++
++ if (!bo || !*bo)
++ return;
++ nvbo = nouveau_bo(*bo);
++ *bo = NULL;
++
++ if (--nvbo->refcount)
++ return;
++
++ if (nvbo->pending) {
++ nvbo->pending = NULL;
++ nouveau_pushbuf_flush(nvbo->pending_channel, 0);
++ }
++
++ nouveau_bo_ufree(nvbo);
++ if (!nouveau_device(nvbo->base.device)->mm_enabled && nvbo->fence)
++ nouveau_fence_signal_cb(nvbo->fence, nouveau_bo_del_cb, nvbo);
++ else
++ nouveau_bo_del_cb(nvbo);
++}
++
++int
++nouveau_bo_ref(struct nouveau_bo *ref, struct nouveau_bo **pbo)
++{
++ if (!pbo)
++ return -EINVAL;
++
++ if (ref)
++ nouveau_bo(ref)->refcount++;
++
++ if (*pbo)
++ nouveau_bo_del(pbo);
++
++ *pbo = ref;
++ return 0;
++}
++
++static int
++nouveau_bo_wait_nomm(struct nouveau_bo *bo, int cpu_write)
++{
++ struct nouveau_bo_priv *nvbo = nouveau_bo(bo);
++ int ret = 0;
++
++ if (cpu_write)
++ ret = nouveau_fence_wait(&nvbo->fence);
++ else
++ ret = nouveau_fence_wait(&nvbo->wr_fence);
++ if (ret)
++ return ret;
++
++ nvbo->write_marker = 0;
++ return 0;
++}
++
++static int
++nouveau_bo_wait(struct nouveau_bo *bo, int cpu_write)
++{
++ struct nouveau_device_priv *nvdev = nouveau_device(bo->device);
++ struct nouveau_bo_priv *nvbo = nouveau_bo(bo);
++ struct drm_nouveau_gem_cpu_prep req;
++ int ret;
++
++ if (!nvbo->global_handle && !nvbo->write_marker && !cpu_write)
++ return 0;
++
++ if (nvbo->pending &&
++ (nvbo->pending->write_domains || cpu_write)) {
++ nvbo->pending = NULL;
++ nouveau_pushbuf_flush(nvbo->pending_channel, 0);
++ }
++
++ if (!nvdev->mm_enabled)
++ return nouveau_bo_wait_nomm(bo, cpu_write);
++
++ req.handle = nvbo->handle;
++ ret = drmCommandWrite(nvdev->fd, DRM_NOUVEAU_GEM_CPU_PREP,
++ &req, sizeof(req));
++ if (ret)
++ return ret;
++
++ nvbo->write_marker = 0;
++ return 0;
++}
++
++int
++nouveau_bo_map(struct nouveau_bo *bo, uint32_t flags)
++{
++ struct nouveau_bo_priv *nvbo = nouveau_bo(bo);
++ int ret;
++
++ if (!nvbo || bo->map)
++ return -EINVAL;
++
++ if (!nouveau_bo_allocated(nvbo)) {
++ if (nvbo->flags & (NOUVEAU_BO_VRAM | NOUVEAU_BO_GART)) {
++ ret = nouveau_bo_kalloc(nvbo, NULL);
++ if (ret)
++ return ret;
++ }
++
++ if (!nouveau_bo_allocated(nvbo)) {
++ ret = nouveau_bo_ualloc(nvbo);
++ if (ret)
++ return ret;
++ }
++ }
++
++ if (nvbo->sysmem) {
++ bo->map = nvbo->sysmem;
++ } else {
++ ret = nouveau_bo_kmap(nvbo);
++ if (ret)
++ return ret;
++
++ ret = nouveau_bo_wait(bo, (flags & NOUVEAU_BO_WR));
++ if (ret)
++ return ret;
++
++ bo->map = nvbo->map;
++ }
++
++ return 0;
++}
++
++void
++nouveau_bo_unmap(struct nouveau_bo *bo)
++{
++ struct nouveau_device_priv *nvdev = nouveau_device(bo->device);
++ struct nouveau_bo_priv *nvbo = nouveau_bo(bo);
++
++ if (nvdev->mm_enabled && bo->map && !nvbo->sysmem) {
++ struct nouveau_device_priv *nvdev = nouveau_device(bo->device);
++ struct drm_nouveau_gem_cpu_fini req;
++
++ req.handle = nvbo->handle;
++ drmCommandWrite(nvdev->fd, DRM_NOUVEAU_GEM_CPU_FINI,
++ &req, sizeof(req));
++ }
++
++ bo->map = NULL;
++}
++
++int
++nouveau_bo_validate_nomm(struct nouveau_bo_priv *nvbo, uint32_t flags)
++{
++ struct nouveau_bo *new = NULL;
++ uint32_t t_handle, t_domain, t_offset, t_size;
++ void *t_map;
++ int ret;
++
++ if ((flags & NOUVEAU_BO_VRAM) && nvbo->domain == NOUVEAU_BO_VRAM)
++ return 0;
++ if ((flags & NOUVEAU_BO_GART) && nvbo->domain == NOUVEAU_BO_GART)
++ return 0;
++ assert(flags & (NOUVEAU_BO_VRAM|NOUVEAU_BO_GART));
++
++ /* Keep tiling info */
++ flags |= (nvbo->flags & (NOUVEAU_BO_TILED|NOUVEAU_BO_ZTILE));
++
++ ret = nouveau_bo_new(nvbo->base.device, flags, 0, nvbo->size, &new);
++ if (ret)
++ return ret;
++
++ ret = nouveau_bo_kalloc(nouveau_bo(new), NULL);
++ if (ret) {
++ nouveau_bo_ref(NULL, &new);
++ return ret;
++ }
++
++ if (nvbo->handle || nvbo->sysmem) {
++ nouveau_bo_kmap(nouveau_bo(new));
++
++ if (!nvbo->base.map) {
++ nouveau_bo_map(&nvbo->base, NOUVEAU_BO_RD);
++ memcpy(nouveau_bo(new)->map, nvbo->base.map, nvbo->base.size);
++ nouveau_bo_unmap(&nvbo->base);
++ } else {
++ memcpy(nouveau_bo(new)->map, nvbo->base.map, nvbo->base.size);
++ }
++ }
++
++ t_handle = nvbo->handle;
++ t_domain = nvbo->domain;
++ t_offset = nvbo->offset;
++ t_size = nvbo->size;
++ t_map = nvbo->map;
++
++ nvbo->handle = nouveau_bo(new)->handle;
++ nvbo->domain = nouveau_bo(new)->domain;
++ nvbo->offset = nouveau_bo(new)->offset;
++ nvbo->size = nouveau_bo(new)->size;
++ nvbo->map = nouveau_bo(new)->map;
++
++ nouveau_bo(new)->handle = t_handle;
++ nouveau_bo(new)->domain = t_domain;
++ nouveau_bo(new)->offset = t_offset;
++ nouveau_bo(new)->size = t_size;
++ nouveau_bo(new)->map = t_map;
++
++ nouveau_bo_ref(NULL, &new);
++
++ return 0;
++}
++
++static int
++nouveau_bo_pin_nomm(struct nouveau_bo *bo, uint32_t flags)
Reply to: