aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorBen Skeggs2010-12-19 18:53:44 -0600
committerBen Skeggs2010-12-20 20:46:51 -0600
commit45cfb9cf089cd56878b1cb5d15391d2470dbeb7c (patch)
tree50a262733e2f1b79d76980aab61eb993dabcbc6a /nouveau
parentba731e7b58911e8caa4e37f0075a677d7ac2afc6 (diff)
downloadlibdrm-45cfb9cf089cd56878b1cb5d15391d2470dbeb7c.tar.gz
libdrm-45cfb9cf089cd56878b1cb5d15391d2470dbeb7c.tar.xz
libdrm-45cfb9cf089cd56878b1cb5d15391d2470dbeb7c.zip
nouveau: split pushbuf macros specific to nv04-nv50 out, and add nvc0
Signed-off-by: Ben Skeggs <bskeggs@redhat.com>
Diffstat (limited to 'nouveau')
-rw-r--r--nouveau/Makefile.am2
-rw-r--r--nouveau/nouveau_grobj.c11
-rw-r--r--nouveau/nouveau_pushbuf.h38
-rw-r--r--nouveau/nv04_pushbuf.h66
-rw-r--r--nouveau/nvc0_pushbuf.h92
5 files changed, 169 insertions, 40 deletions
diff --git a/nouveau/Makefile.am b/nouveau/Makefile.am
index de3f4df0..8b899164 100644
--- a/nouveau/Makefile.am
+++ b/nouveau/Makefile.am
@@ -28,6 +28,8 @@ libdrm_nouveaucommoninclude_HEADERS = \
28 nouveau_grobj.h \ 28 nouveau_grobj.h \
29 nouveau_notifier.h \ 29 nouveau_notifier.h \
30 nouveau_pushbuf.h \ 30 nouveau_pushbuf.h \
31 nv04_pushbuf.h \
32 nvc0_pushbuf.h \
31 nouveau_bo.h \ 33 nouveau_bo.h \
32 nouveau_resource.h \ 34 nouveau_resource.h \
33 nouveau_reloc.h 35 nouveau_reloc.h
diff --git a/nouveau/nouveau_grobj.c b/nouveau/nouveau_grobj.c
index df2ffb91..c6b98f16 100644
--- a/nouveau/nouveau_grobj.c
+++ b/nouveau/nouveau_grobj.c
@@ -112,6 +112,7 @@ nouveau_grobj_free(struct nouveau_grobj **grobj)
112void 112void
113nouveau_grobj_autobind(struct nouveau_grobj *grobj) 113nouveau_grobj_autobind(struct nouveau_grobj *grobj)
114{ 114{
115 struct nouveau_channel *chan = grobj->channel;
115 struct nouveau_subchannel *subc = NULL; 116 struct nouveau_subchannel *subc = NULL;
116 int i; 117 int i;
117 118
@@ -134,7 +135,13 @@ nouveau_grobj_autobind(struct nouveau_grobj *grobj)
134 subc->gr->bound = NOUVEAU_GROBJ_BOUND; 135 subc->gr->bound = NOUVEAU_GROBJ_BOUND;
135 subc->gr->subc = subc - &grobj->channel->subc[0]; 136 subc->gr->subc = subc - &grobj->channel->subc[0];
136 137
137 BEGIN_RING(grobj->channel, grobj, 0x0000, 1); 138 WAIT_RING(chan, 2);
138 OUT_RING (grobj->channel, grobj->handle); 139 if (chan->device->chipset < 0xc0) {
140 OUT_RING (chan, (1 << 18) | (grobj->subc << 13));
141 OUT_RING (chan, grobj->handle);
142 } else {
143 OUT_RING (chan, (2 << 28) | (1 << 16) | (grobj->subc << 13));
144 OUT_RING (chan, grobj->grclass);
145 }
139} 146}
140 147
diff --git a/nouveau/nouveau_pushbuf.h b/nouveau/nouveau_pushbuf.h
index 52d13a0a..2a98789c 100644
--- a/nouveau/nouveau_pushbuf.h
+++ b/nouveau/nouveau_pushbuf.h
@@ -96,49 +96,11 @@ WAIT_RING(struct nouveau_channel *chan, unsigned size)
96} 96}
97 97
98static __inline__ void 98static __inline__ void
99BEGIN_RING(struct nouveau_channel *chan, struct nouveau_grobj *gr,
100 unsigned mthd, unsigned size)
101{
102 if (gr->bound == NOUVEAU_GROBJ_UNBOUND)
103 nouveau_grobj_autobind(gr);
104 chan->subc[gr->subc].sequence = chan->subc_sequence++;
105
106 WAIT_RING(chan, size + 1);
107 OUT_RING(chan, (gr->subc << 13) | (size << 18) | mthd);
108}
109
110/* non-incrementing BEGIN_RING */
111static __inline__ void
112BEGIN_RING_NI(struct nouveau_channel *chan, struct nouveau_grobj *gr,
113 unsigned mthd, unsigned size)
114{
115 BEGIN_RING(chan, gr, mthd | 0x40000000, size);
116}
117
118static __inline__ void
119FIRE_RING(struct nouveau_channel *chan) 99FIRE_RING(struct nouveau_channel *chan)
120{ 100{
121 nouveau_pushbuf_flush(chan, 0); 101 nouveau_pushbuf_flush(chan, 0);
122} 102}
123 103
124static __inline__ void
125BIND_RING(struct nouveau_channel *chan, struct nouveau_grobj *gr, unsigned sc)
126{
127 struct nouveau_subchannel *subc = &gr->channel->subc[sc];
128
129 if (subc->gr) {
130 if (subc->gr->bound == NOUVEAU_GROBJ_BOUND_EXPLICIT)
131 assert(0);
132 subc->gr->bound = NOUVEAU_GROBJ_UNBOUND;
133 }
134 subc->gr = gr;
135 subc->gr->subc = sc;
136 subc->gr->bound = NOUVEAU_GROBJ_BOUND_EXPLICIT;
137
138 BEGIN_RING(chan, gr, 0x0000, 1);
139 OUT_RING (chan, gr->handle);
140}
141
142static __inline__ int 104static __inline__ int
143OUT_RELOC(struct nouveau_channel *chan, struct nouveau_bo *bo, 105OUT_RELOC(struct nouveau_channel *chan, struct nouveau_bo *bo,
144 unsigned data, unsigned flags, unsigned vor, unsigned tor) 106 unsigned data, unsigned flags, unsigned vor, unsigned tor)
diff --git a/nouveau/nv04_pushbuf.h b/nouveau/nv04_pushbuf.h
new file mode 100644
index 00000000..586b2847
--- /dev/null
+++ b/nouveau/nv04_pushbuf.h
@@ -0,0 +1,66 @@
1/*
2 * Copyright 2007 Nouveau Project
3 *
4 * Permission is hereby granted, free of charge, to any person obtaining a
5 * copy of this software and associated documentation files (the "Software"),
6 * to deal in the Software without restriction, including without limitation
7 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
8 * and/or sell copies of the Software, and to permit persons to whom the
9 * Software is furnished to do so, subject to the following conditions:
10 *
11 * The above copyright notice and this permission notice shall be included in
12 * all copies or substantial portions of the Software.
13 *
14 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
15 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
16 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
17 * THE AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
18 * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF
19 * OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
20 * SOFTWARE.
21 */
22
23#ifndef __NV04_PUSHBUF_H__
24#define __NV04_PUSHBUF_H__
25
26#include "nouveau_pushbuf.h"
27
28static __inline__ void
29BEGIN_RING(struct nouveau_channel *chan, struct nouveau_grobj *gr,
30 unsigned mthd, unsigned size)
31{
32 if (gr->bound == NOUVEAU_GROBJ_UNBOUND)
33 nouveau_grobj_autobind(gr);
34 chan->subc[gr->subc].sequence = chan->subc_sequence++;
35
36 WAIT_RING(chan, size + 1);
37 OUT_RING(chan, (gr->subc << 13) | (size << 18) | mthd);
38}
39
40/* non-incrementing BEGIN_RING */
41static __inline__ void
42BEGIN_RING_NI(struct nouveau_channel *chan, struct nouveau_grobj *gr,
43 unsigned mthd, unsigned size)
44{
45 BEGIN_RING(chan, gr, mthd | 0x40000000, size);
46}
47
48static __inline__ void
49BIND_RING(struct nouveau_channel *chan, struct nouveau_grobj *gr, unsigned sc)
50{
51 struct nouveau_subchannel *subc = &gr->channel->subc[sc];
52
53 if (subc->gr) {
54 if (subc->gr->bound == NOUVEAU_GROBJ_BOUND_EXPLICIT)
55 assert(0);
56 subc->gr->bound = NOUVEAU_GROBJ_UNBOUND;
57 }
58 subc->gr = gr;
59 subc->gr->subc = sc;
60 subc->gr->bound = NOUVEAU_GROBJ_BOUND_EXPLICIT;
61
62 BEGIN_RING(chan, gr, 0x0000, 1);
63 OUT_RING (chan, gr->handle);
64}
65
66#endif
diff --git a/nouveau/nvc0_pushbuf.h b/nouveau/nvc0_pushbuf.h
new file mode 100644
index 00000000..40dc7e67
--- /dev/null
+++ b/nouveau/nvc0_pushbuf.h
@@ -0,0 +1,92 @@
1/*
2 * Copyright 2010 Nouveau Project
3 *
4 * Permission is hereby granted, free of charge, to any person obtaining a
5 * copy of this software and associated documentation files (the "Software"),
6 * to deal in the Software without restriction, including without limitation
7 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
8 * and/or sell copies of the Software, and to permit persons to whom the
9 * Software is furnished to do so, subject to the following conditions:
10 *
11 * The above copyright notice and this permission notice shall be included in
12 * all copies or substantial portions of the Software.
13 *
14 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
15 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
16 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
17 * THE AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
18 * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF
19 * OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
20 * SOFTWARE.
21 */
22
23#ifndef __NVC0_PUSHBUF_H__
24#define __NVC0_PUSHBUF_H__
25
26#include "nouveau_pushbuf.h"
27
28#define SUBC_BIND(chan, gr) do { \
29 if (gr->bound == NOUVEAU_GROBJ_UNBOUND) \
30 nouveau_grobj_autobind(gr); \
31 chan->subc[gr->subc].sequence = chan->subc_sequence++; \
32} while (0)
33
34/* incremental methods */
35static __inline__ void
36BEGIN_RING(struct nouveau_channel *chan, struct nouveau_grobj *gr,
37 unsigned mthd, unsigned size)
38{
39 SUBC_BIND(chan, gr);
40 WAIT_RING(chan, size + 1);
41 OUT_RING (chan, (0x2 << 28) | (size << 16) | (gr->subc << 13) | (mthd >> 2));
42}
43
44/* non-incremental */
45static __inline__ void
46BEGIN_RING_NI(struct nouveau_channel *chan, struct nouveau_grobj *gr,
47 unsigned mthd, unsigned size)
48{
49 SUBC_BIND(chan, gr);
50 WAIT_RING(chan, size + 1);
51 OUT_RING (chan, (0x6 << 28) | (size << 16) | (gr->subc << 13) | (mthd >> 2));
52}
53
54/* increment-once */
55static __inline__ void
56BEGIN_RING_1I(struct nouveau_channel *chan, struct nouveau_grobj *gr,
57 unsigned mthd, unsigned size)
58{
59 SUBC_BIND(chan, gr);
60 WAIT_RING(chan, size + 1);
61 OUT_RING (chan, (0xa << 28) | (size << 16) | (gr->subc << 13) | (mthd >> 2));
62}
63
64/* inline-data */
65static __inline__ void
66IMMED_RING(struct nouveau_channel *chan, struct nouveau_grobj *gr,
67 unsigned mthd, unsigned data)
68{
69 SUBC_BIND(chan, gr);
70 WAIT_RING(chan, 1);
71 OUT_RING (chan, (0x8 << 28) | (data << 16) | (gr->subc << 13) | (mthd >> 2));
72}
73
74static __inline__ void
75BIND_RING(struct nouveau_channel *chan, struct nouveau_grobj *gr, unsigned sc)
76{
77 struct nouveau_subchannel *subc = &gr->channel->subc[sc];
78
79 if (subc->gr) {
80 if (subc->gr->bound == NOUVEAU_GROBJ_BOUND_EXPLICIT)
81 assert(0);
82 subc->gr->bound = NOUVEAU_GROBJ_UNBOUND;
83 }
84 subc->gr = gr;
85 subc->gr->subc = sc;
86 subc->gr->bound = NOUVEAU_GROBJ_BOUND_EXPLICIT;
87
88 BEGIN_RING(chan, gr, 0x0000, 1);
89 OUT_RING (chan, gr->grclass);
90}
91
92#endif