Merge commit 'origin/gallium-0.1' into gallium-0.2
[mesa.git] / src / gallium / include / pipe / p_inlines.h
1 /**************************************************************************
2 *
3 * Copyright 2007 Tungsten Graphics, Inc., Cedar Park, Texas.
4 * All Rights Reserved.
5 *
6 * Permission is hereby granted, free of charge, to any person obtaining a
7 * copy of this software and associated documentation files (the
8 * "Software"), to deal in the Software without restriction, including
9 * without limitation the rights to use, copy, modify, merge, publish,
10 * distribute, sub license, and/or sell copies of the Software, and to
11 * permit persons to whom the Software is furnished to do so, subject to
12 * the following conditions:
13 *
14 * The above copyright notice and this permission notice (including the
15 * next paragraph) shall be included in all copies or substantial portions
16 * of the Software.
17 *
18 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
19 * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
20 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT.
21 * IN NO EVENT SHALL TUNGSTEN GRAPHICS AND/OR ITS SUPPLIERS BE LIABLE FOR
22 * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
23 * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
24 * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
25 *
26 **************************************************************************/
27
28 #ifndef P_INLINES_H
29 #define P_INLINES_H
30
31 #include "p_context.h"
32 #include "p_defines.h"
33 #include "p_screen.h"
34 #include "p_winsys.h"
35
36
37 #ifdef __cplusplus
38 extern "C" {
39 #endif
40
41
42 /* XXX: these are a kludge. will fix when all surfaces are views into
43 * textures, and free-floating winsys surfaces go away.
44 */
45 static INLINE void *
46 pipe_surface_map( struct pipe_surface *surf, unsigned flags )
47 {
48 if (surf->texture) {
49 struct pipe_screen *screen = surf->texture->screen;
50 return surf->texture->screen->surface_map( screen, surf, flags );
51 }
52 else {
53 struct pipe_winsys *winsys = surf->winsys;
54 char *map = (char *)winsys->buffer_map( winsys, surf->buffer, flags );
55 if (map == NULL)
56 return NULL;
57 return (void *)(map + surf->offset);
58 }
59 }
60
61 static INLINE void
62 pipe_surface_unmap( struct pipe_surface *surf )
63 {
64 if (surf->texture) {
65 struct pipe_screen *screen = surf->texture->screen;
66 surf->texture->screen->surface_unmap( screen, surf );
67 }
68 else {
69 struct pipe_winsys *winsys = surf->winsys;
70 winsys->buffer_unmap( winsys, surf->buffer );
71 }
72 }
73
74
75
76 /**
77 * Set 'ptr' to point to 'surf' and update reference counting.
78 * The old thing pointed to, if any, will be unreferenced first.
79 * 'surf' may be NULL.
80 */
81 static INLINE void
82 pipe_surface_reference(struct pipe_surface **ptr, struct pipe_surface *surf)
83 {
84 /* bump the refcount first */
85 if (surf) {
86 assert(surf->refcount);
87 surf->refcount++;
88 }
89
90 if (*ptr) {
91 assert((*ptr)->refcount);
92
93 /* There are currently two sorts of surfaces... This needs to be
94 * fixed so that all surfaces are views into a texture.
95 */
96 if ((*ptr)->texture) {
97 struct pipe_screen *screen = (*ptr)->texture->screen;
98 screen->tex_surface_release( screen, ptr );
99 }
100 else {
101 struct pipe_winsys *winsys = (*ptr)->winsys;
102 winsys->surface_release(winsys, ptr);
103 }
104
105 assert(!*ptr);
106 }
107
108 *ptr = surf;
109 }
110
111
112 /* XXX: thread safety issues!
113 */
114 static INLINE void
115 winsys_buffer_reference(struct pipe_winsys *winsys,
116 struct pipe_buffer **ptr,
117 struct pipe_buffer *buf)
118 {
119 if (buf) {
120 assert(buf->refcount);
121 buf->refcount++;
122 }
123
124 if (*ptr) {
125 assert((*ptr)->refcount);
126 if(--(*ptr)->refcount == 0)
127 winsys->buffer_destroy( winsys, *ptr );
128 }
129
130 *ptr = buf;
131 }
132
133
134
135 /**
136 * \sa pipe_surface_reference
137 */
138 static INLINE void
139 pipe_texture_reference(struct pipe_texture **ptr,
140 struct pipe_texture *pt)
141 {
142 assert(ptr);
143
144 if (pt) {
145 assert(pt->refcount);
146 pt->refcount++;
147 }
148
149 if (*ptr) {
150 struct pipe_screen *screen = (*ptr)->screen;
151 assert(screen);
152 assert((*ptr)->refcount);
153 screen->texture_release(screen, ptr);
154
155 assert(!*ptr);
156 }
157
158 *ptr = pt;
159 }
160
161
162 static INLINE void
163 pipe_texture_release(struct pipe_texture **ptr)
164 {
165 struct pipe_screen *screen;
166 assert(ptr);
167 screen = (*ptr)->screen;
168 assert((*ptr)->refcount);
169 screen->texture_release(screen, ptr);
170 *ptr = NULL;
171 }
172
173
174 /**
175 * Convenience wrappers for winsys buffer functions.
176 */
177
178 static INLINE struct pipe_buffer *
179 pipe_buffer_create( struct pipe_screen *screen,
180 unsigned alignment, unsigned usage, unsigned size )
181 {
182 return screen->winsys->buffer_create(screen->winsys, alignment, usage, size);
183 }
184
185 static INLINE struct pipe_buffer *
186 pipe_user_buffer_create( struct pipe_screen *screen, void *ptr, unsigned size )
187 {
188 return screen->winsys->user_buffer_create(screen->winsys, ptr, size);
189 }
190
191 static INLINE void *
192 pipe_buffer_map(struct pipe_screen *screen,
193 struct pipe_buffer *buf,
194 unsigned usage)
195 {
196 return screen->winsys->buffer_map(screen->winsys, buf, usage);
197 }
198
199 static INLINE void
200 pipe_buffer_unmap(struct pipe_screen *screen,
201 struct pipe_buffer *buf)
202 {
203 screen->winsys->buffer_unmap(screen->winsys, buf);
204 }
205
206 /* XXX when we're using this everywhere, get rid of
207 * winsys_buffer_reference() above.
208 */
209 static INLINE void
210 pipe_buffer_reference(struct pipe_screen *screen,
211 struct pipe_buffer **ptr,
212 struct pipe_buffer *buf)
213 {
214 winsys_buffer_reference(screen->winsys, ptr, buf);
215 }
216
217
218 #ifdef __cplusplus
219 }
220 #endif
221
222 #endif /* P_INLINES_H */