2 #include "main/glheader.h"
3 #include "main/macros.h"
4 #include "main/mfeatures.h"
5 #include "main/mtypes.h"
6 #include "main/enums.h"
7 #include "main/bufferobj.h"
8 #include "main/context.h"
9 #include "main/formats.h"
11 #include "main/renderbuffer.h"
12 #include "main/texcompress.h"
13 #include "main/texgetimage.h"
14 #include "main/texobj.h"
15 #include "main/teximage.h"
16 #include "main/texstore.h"
18 #include "intel_context.h"
19 #include "intel_mipmap_tree.h"
20 #include "intel_buffer_objects.h"
21 #include "intel_batchbuffer.h"
22 #include "intel_tex.h"
23 #include "intel_blit.h"
24 #include "intel_fbo.h"
25 #include "intel_span.h"
28 #include "brw_context.h"
31 #define FILE_DEBUG_FLAG DEBUG_TEXTURE
33 /* Work back from the specified level of the image to the baselevel and create a
34 * miptree of that size.
36 struct intel_mipmap_tree
*
37 intel_miptree_create_for_teximage(struct intel_context
*intel
,
38 struct intel_texture_object
*intelObj
,
39 struct intel_texture_image
*intelImage
,
40 bool expect_accelerated_upload
)
44 int width
, height
, depth
;
47 intel_miptree_get_dimensions_for_image(&intelImage
->base
.Base
,
48 &width
, &height
, &depth
);
50 DBG("%s\n", __FUNCTION__
);
52 if (intelImage
->base
.Base
.Level
> intelObj
->base
.BaseLevel
&&
54 (intelObj
->base
.Target
!= GL_TEXTURE_1D
&& height
== 1) ||
55 (intelObj
->base
.Target
== GL_TEXTURE_3D
&& depth
== 1))) {
56 /* For this combination, we're at some lower mipmap level and
57 * some important dimension is 1. We can't extrapolate up to a
58 * likely base level width/height/depth for a full mipmap stack
59 * from this info, so just allocate this one level.
61 firstLevel
= intelImage
->base
.Base
.Level
;
62 lastLevel
= intelImage
->base
.Base
.Level
;
64 /* If this image disrespects BaseLevel, allocate from level zero.
65 * Usually BaseLevel == 0, so it's unlikely to happen.
67 if (intelImage
->base
.Base
.Level
< intelObj
->base
.BaseLevel
)
70 firstLevel
= intelObj
->base
.BaseLevel
;
72 /* Figure out image dimensions at start level. */
73 for (i
= intelImage
->base
.Base
.Level
; i
> firstLevel
; i
--) {
81 /* Guess a reasonable value for lastLevel. This is probably going
82 * to be wrong fairly often and might mean that we have to look at
83 * resizable buffers, or require that buffers implement lazy
84 * pagetable arrangements.
86 if ((intelObj
->base
.Sampler
.MinFilter
== GL_NEAREST
||
87 intelObj
->base
.Sampler
.MinFilter
== GL_LINEAR
) &&
88 intelImage
->base
.Base
.Level
== firstLevel
&&
89 (intel
->gen
< 4 || firstLevel
== 0)) {
90 lastLevel
= firstLevel
;
92 lastLevel
= (firstLevel
+
93 _mesa_get_tex_max_num_levels(intelObj
->base
.Target
,
94 width
, height
, depth
) - 1);
98 return intel_miptree_create(intel
,
99 intelObj
->base
.Target
,
100 intelImage
->base
.Base
.TexFormat
,
106 expect_accelerated_upload
,
107 intelImage
->base
.Base
.NumSamples
,
108 false /* force_y_tiling */);
111 /* There are actually quite a few combinations this will work for,
112 * more than what I've listed here.
115 check_pbo_format(GLenum format
, GLenum type
,
116 gl_format mesa_format
)
118 switch (mesa_format
) {
119 case MESA_FORMAT_ARGB8888
:
120 return (format
== GL_BGRA
&& (type
== GL_UNSIGNED_BYTE
||
121 type
== GL_UNSIGNED_INT_8_8_8_8_REV
));
122 case MESA_FORMAT_RGB565
:
123 return (format
== GL_RGB
&& type
== GL_UNSIGNED_SHORT_5_6_5
);
125 return (format
== GL_LUMINANCE
&& type
== GL_UNSIGNED_BYTE
);
126 case MESA_FORMAT_YCBCR
:
127 return (type
== GL_UNSIGNED_SHORT_8_8_MESA
|| type
== GL_UNSIGNED_BYTE
);
134 /* XXX: Do this for TexSubImage also:
137 try_pbo_upload(struct gl_context
*ctx
,
138 struct gl_texture_image
*image
,
139 const struct gl_pixelstore_attrib
*unpack
,
140 GLenum format
, GLenum type
, const void *pixels
)
142 struct intel_texture_image
*intelImage
= intel_texture_image(image
);
143 struct intel_context
*intel
= intel_context(ctx
);
144 struct intel_buffer_object
*pbo
= intel_buffer_object(unpack
->BufferObj
);
145 GLuint src_offset
, src_stride
;
147 drm_intel_bo
*dst_buffer
, *src_buffer
;
149 if (!_mesa_is_bufferobj(unpack
->BufferObj
))
152 DBG("trying pbo upload\n");
154 if (intel
->ctx
._ImageTransferState
||
155 unpack
->SkipPixels
|| unpack
->SkipRows
) {
156 DBG("%s: image transfer\n", __FUNCTION__
);
160 if (!check_pbo_format(format
, type
, intelImage
->base
.Base
.TexFormat
)) {
161 DBG("%s: format mismatch (upload to %s with format 0x%x, type 0x%x)\n",
162 __FUNCTION__
, _mesa_get_format_name(intelImage
->base
.Base
.TexFormat
),
167 ctx
->Driver
.AllocTextureImageBuffer(ctx
, image
);
169 if (!intelImage
->mt
) {
170 DBG("%s: no miptree\n", __FUNCTION__
);
174 if (image
->TexObject
->Target
== GL_TEXTURE_1D_ARRAY
||
175 image
->TexObject
->Target
== GL_TEXTURE_2D_ARRAY
) {
176 DBG("%s: no support for array textures\n", __FUNCTION__
);
180 dst_buffer
= intelImage
->mt
->region
->bo
;
181 src_buffer
= intel_bufferobj_source(intel
, pbo
, 64, &src_offset
);
182 /* note: potential 64-bit ptr to 32-bit int cast */
183 src_offset
+= (GLuint
) (unsigned long) pixels
;
185 if (unpack
->RowLength
> 0)
186 src_stride
= unpack
->RowLength
;
188 src_stride
= image
->Width
;
189 src_stride
*= intelImage
->mt
->region
->cpp
;
191 intel_miptree_get_image_offset(intelImage
->mt
, intelImage
->base
.Base
.Level
,
192 intelImage
->base
.Base
.Face
,
195 if (!intelEmitCopyBlit(intel
,
197 src_stride
, src_buffer
,
199 intelImage
->mt
->region
->pitch
, dst_buffer
, 0,
200 intelImage
->mt
->region
->tiling
,
201 0, 0, dst_x
, dst_y
, image
->Width
, image
->Height
,
203 DBG("%s: blit failed\n", __FUNCTION__
);
207 DBG("%s: success\n", __FUNCTION__
);
212 intelTexImage(struct gl_context
* ctx
,
214 struct gl_texture_image
*texImage
,
215 GLenum format
, GLenum type
, const void *pixels
,
216 const struct gl_pixelstore_attrib
*unpack
)
220 DBG("%s target %s level %d %dx%dx%d\n", __FUNCTION__
,
221 _mesa_lookup_enum_by_nr(texImage
->TexObject
->Target
),
222 texImage
->Level
, texImage
->Width
, texImage
->Height
, texImage
->Depth
);
224 ok
= intel_texsubimage_tiled_memcpy(ctx
, dims
, texImage
,
225 0, 0, 0, /*x,y,z offsets*/
229 format
, type
, pixels
, unpack
,
230 true /*for_glTexImage*/);
234 /* Attempt to use the blitter for PBO image uploads.
237 try_pbo_upload(ctx
, texImage
, unpack
, format
, type
, pixels
)) {
241 DBG("%s: upload image %dx%dx%d pixels %p\n",
242 __FUNCTION__
, texImage
->Width
, texImage
->Height
, texImage
->Depth
,
245 _mesa_store_teximage(ctx
, dims
, texImage
,
246 format
, type
, pixels
, unpack
);
251 * Binds a region to a texture image, like it was uploaded by glTexImage2D().
253 * Used for GLX_EXT_texture_from_pixmap and EGL image extensions,
256 intel_set_texture_image_region(struct gl_context
*ctx
,
257 struct gl_texture_image
*image
,
258 struct intel_region
*region
,
260 GLenum internalFormat
,
268 struct intel_context
*intel
= intel_context(ctx
);
269 struct intel_texture_image
*intel_image
= intel_texture_image(image
);
270 struct gl_texture_object
*texobj
= image
->TexObject
;
271 struct intel_texture_object
*intel_texobj
= intel_texture_object(texobj
);
272 bool has_surface_tile_offset
= false;
273 uint32_t draw_x
, draw_y
;
275 _mesa_init_teximage_fields(&intel
->ctx
, image
,
277 0, internalFormat
, format
);
279 ctx
->Driver
.FreeTextureImageBuffer(ctx
, image
);
281 intel_image
->mt
= intel_miptree_create_layout(intel
, target
, image
->TexFormat
,
284 true, 0 /* num_samples */);
285 if (intel_image
->mt
== NULL
)
287 intel_region_reference(&intel_image
->mt
->region
, region
);
288 intel_image
->mt
->total_width
= width
;
289 intel_image
->mt
->total_height
= height
;
290 intel_image
->mt
->level
[0].slice
[0].x_offset
= tile_x
;
291 intel_image
->mt
->level
[0].slice
[0].y_offset
= tile_y
;
293 intel_miptree_get_tile_offsets(intel_image
->mt
, 0, 0, &draw_x
, &draw_y
);
295 has_surface_tile_offset
= brw_context(ctx
)->has_surface_tile_offset
;
298 /* From "OES_EGL_image" error reporting. We report GL_INVALID_OPERATION
299 * for EGL images from non-tile aligned sufaces in gen4 hw and earlier which has
300 * trouble resolving back to destination image due to alignment issues.
302 if (!has_surface_tile_offset
&&
303 (draw_x
!= 0 || draw_y
!= 0)) {
304 _mesa_error(ctx
, GL_INVALID_OPERATION
, __func__
);
305 intel_miptree_release(&intel_image
->mt
);
309 intel_texobj
->needs_validate
= true;
311 intel_image
->mt
->offset
= offset
;
312 assert(region
->pitch
% region
->cpp
== 0);
313 intel_image
->base
.RowStride
= region
->pitch
/ region
->cpp
;
315 /* Immediately validate the image to the object. */
316 intel_miptree_reference(&intel_texobj
->mt
, intel_image
->mt
);
320 intelSetTexBuffer2(__DRIcontext
*pDRICtx
, GLint target
,
321 GLint texture_format
,
322 __DRIdrawable
*dPriv
)
324 struct gl_framebuffer
*fb
= dPriv
->driverPrivate
;
325 struct intel_context
*intel
= pDRICtx
->driverPrivate
;
326 struct gl_context
*ctx
= &intel
->ctx
;
327 struct intel_texture_object
*intelObj
;
328 struct intel_renderbuffer
*rb
;
329 struct gl_texture_object
*texObj
;
330 struct gl_texture_image
*texImage
;
331 int level
= 0, internalFormat
= 0;
332 gl_format texFormat
= MESA_FORMAT_NONE
;
334 texObj
= _mesa_get_current_tex_object(ctx
, target
);
335 intelObj
= intel_texture_object(texObj
);
340 if (dPriv
->lastStamp
!= dPriv
->dri2
.stamp
||
341 !pDRICtx
->driScreenPriv
->dri2
.useInvalidate
)
342 intel_update_renderbuffers(pDRICtx
, dPriv
);
344 rb
= intel_get_renderbuffer(fb
, BUFFER_FRONT_LEFT
);
345 /* If the region isn't set, then intel_update_renderbuffers was unable
346 * to get the buffers for the drawable.
351 if (rb
->mt
->cpp
== 4) {
352 if (texture_format
== __DRI_TEXTURE_FORMAT_RGB
) {
353 internalFormat
= GL_RGB
;
354 texFormat
= MESA_FORMAT_XRGB8888
;
357 internalFormat
= GL_RGBA
;
358 texFormat
= MESA_FORMAT_ARGB8888
;
360 } else if (rb
->mt
->cpp
== 2) {
361 internalFormat
= GL_RGB
;
362 texFormat
= MESA_FORMAT_RGB565
;
365 _mesa_lock_texture(&intel
->ctx
, texObj
);
366 texImage
= _mesa_get_tex_image(ctx
, texObj
, target
, level
);
367 intel_set_texture_image_region(ctx
, texImage
, rb
->mt
->region
, target
,
368 internalFormat
, texFormat
, 0,
369 rb
->mt
->region
->width
,
370 rb
->mt
->region
->height
,
372 _mesa_unlock_texture(&intel
->ctx
, texObj
);
376 intelSetTexBuffer(__DRIcontext
*pDRICtx
, GLint target
, __DRIdrawable
*dPriv
)
378 /* The old interface didn't have the format argument, so copy our
379 * implementation's behavior at the time.
381 intelSetTexBuffer2(pDRICtx
, target
, __DRI_TEXTURE_FORMAT_RGBA
, dPriv
);
385 intel_image_target_texture_2d(struct gl_context
*ctx
, GLenum target
,
386 struct gl_texture_object
*texObj
,
387 struct gl_texture_image
*texImage
,
388 GLeglImageOES image_handle
)
390 struct intel_context
*intel
= intel_context(ctx
);
394 screen
= intel
->intelScreen
->driScrnPriv
;
395 image
= screen
->dri2
.image
->lookupEGLImage(screen
, image_handle
,
396 screen
->loaderPrivate
);
400 /* Disallow depth/stencil textures: we don't have a way to pass the
401 * separate stencil miptree of a GL_DEPTH_STENCIL texture through.
403 if (image
->has_depthstencil
) {
404 _mesa_error(ctx
, GL_INVALID_OPERATION
, __func__
);
408 intel_set_texture_image_region(ctx
, texImage
, image
->region
,
409 target
, image
->internal_format
,
410 image
->format
, image
->offset
,
411 image
->width
, image
->height
,
412 image
->tile_x
, image
->tile_y
);
416 intelInitTextureImageFuncs(struct dd_function_table
*functions
)
418 functions
->TexImage
= intelTexImage
;
419 functions
->EGLImageTargetTexture2D
= intel_image_target_texture_2d
;