mirror of
https://gitlab.freedesktop.org/mesa/mesa.git
synced 2026-05-07 20:08:06 +02:00
i915g: Fix cubemap layouts
This commit is contained in:
parent
762ed4db47
commit
ed94e744d3
1 changed files with 121 additions and 101 deletions
|
|
@ -55,26 +55,39 @@
|
||||||
* Initial offset for Cube map.
|
* Initial offset for Cube map.
|
||||||
*/
|
*/
|
||||||
static const int initial_offsets[6][2] = {
|
static const int initial_offsets[6][2] = {
|
||||||
{0, 0},
|
[PIPE_TEX_FACE_POS_X] = {0, 0},
|
||||||
{0, 2},
|
[PIPE_TEX_FACE_POS_Y] = {1, 0},
|
||||||
{1, 0},
|
[PIPE_TEX_FACE_POS_Z] = {1, 1},
|
||||||
{1, 2},
|
[PIPE_TEX_FACE_NEG_X] = {0, 2},
|
||||||
{1, 1},
|
[PIPE_TEX_FACE_NEG_Y] = {1, 2},
|
||||||
{1, 3}
|
[PIPE_TEX_FACE_NEG_Z] = {1, 3},
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Step offsets for Cube map.
|
* Step offsets for Cube map.
|
||||||
*/
|
*/
|
||||||
static const int step_offsets[6][2] = {
|
static const int step_offsets[6][2] = {
|
||||||
{0, 2},
|
[PIPE_TEX_FACE_POS_X] = { 0, 2},
|
||||||
{0, 2},
|
[PIPE_TEX_FACE_POS_Y] = {-1, 2},
|
||||||
{-1, 2},
|
[PIPE_TEX_FACE_POS_Z] = {-1, 1},
|
||||||
{-1, 2},
|
[PIPE_TEX_FACE_NEG_X] = { 0, 2},
|
||||||
{-1, 1},
|
[PIPE_TEX_FACE_NEG_Y] = {-1, 2},
|
||||||
{-1, 1}
|
[PIPE_TEX_FACE_NEG_Z] = {-1, 1},
|
||||||
};
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* For compressed level 2
|
||||||
|
*/
|
||||||
|
static const int bottom_offsets[6] = {
|
||||||
|
[PIPE_TEX_FACE_POS_X] = 16 + 0 * 8,
|
||||||
|
[PIPE_TEX_FACE_POS_Y] = 16 + 1 * 8,
|
||||||
|
[PIPE_TEX_FACE_POS_Z] = 16 + 2 * 8,
|
||||||
|
[PIPE_TEX_FACE_NEG_X] = 16 + 3 * 8,
|
||||||
|
[PIPE_TEX_FACE_NEG_Y] = 16 + 4 * 8,
|
||||||
|
[PIPE_TEX_FACE_NEG_Z] = 16 + 5 * 8,
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
/* XXX really need twice the size if x is already pot?
|
/* XXX really need twice the size if x is already pot?
|
||||||
Otherwise just use util_next_power_of_two?
|
Otherwise just use util_next_power_of_two?
|
||||||
*/
|
*/
|
||||||
|
|
@ -221,6 +234,40 @@ i9x5_special_layout(struct i915_texture *tex)
|
||||||
return FALSE;
|
return FALSE;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Cube layout used on i915 and for non-compressed textures on i945.
|
||||||
|
*/
|
||||||
|
static void
|
||||||
|
i9x5_texture_layout_cube(struct i915_texture *tex)
|
||||||
|
{
|
||||||
|
struct pipe_resource *pt = &tex->b.b;
|
||||||
|
const unsigned nblocks = util_format_get_nblocksx(pt->format, pt->width0);
|
||||||
|
unsigned level;
|
||||||
|
unsigned face;
|
||||||
|
|
||||||
|
assert(pt->width0 == pt->height0); /* cubemap images are square */
|
||||||
|
|
||||||
|
/* double pitch for cube layouts */
|
||||||
|
tex->stride = align(nblocks * util_format_get_blocksize(pt->format) * 2, 4);
|
||||||
|
tex->total_nblocksy = nblocks * 4;
|
||||||
|
|
||||||
|
for (level = 0; level <= pt->last_level; level++)
|
||||||
|
i915_texture_set_level_info(tex, level, 6);
|
||||||
|
|
||||||
|
for (face = 0; face < 6; face++) {
|
||||||
|
unsigned x = initial_offsets[face][0] * nblocks;
|
||||||
|
unsigned y = initial_offsets[face][1] * nblocks;
|
||||||
|
unsigned d = nblocks;
|
||||||
|
|
||||||
|
for (level = 0; level <= pt->last_level; level++) {
|
||||||
|
i915_texture_set_image_offset(tex, level, face, x, y);
|
||||||
|
d >>= 1;
|
||||||
|
x += step_offsets[face][0] * d;
|
||||||
|
y += step_offsets[face][1] * d;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* i915 layout functions
|
* i915 layout functions
|
||||||
|
|
@ -300,37 +347,6 @@ i915_texture_layout_3d(struct i915_texture *tex)
|
||||||
tex->total_nblocksy = stack_nblocksy * pt->depth0;
|
tex->total_nblocksy = stack_nblocksy * pt->depth0;
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
|
||||||
i915_texture_layout_cube(struct i915_texture *tex)
|
|
||||||
{
|
|
||||||
struct pipe_resource *pt = &tex->b.b;
|
|
||||||
const unsigned nblocks = util_format_get_nblocksx(pt->format, pt->width0);
|
|
||||||
unsigned level;
|
|
||||||
unsigned face;
|
|
||||||
|
|
||||||
assert(pt->width0 == pt->height0); /* cubemap images are square */
|
|
||||||
|
|
||||||
/* double pitch for cube layouts */
|
|
||||||
tex->stride = align(nblocks * util_format_get_blocksize(pt->format) * 2, 4);
|
|
||||||
tex->total_nblocksy = nblocks * 4;
|
|
||||||
|
|
||||||
for (level = 0; level <= pt->last_level; level++)
|
|
||||||
i915_texture_set_level_info(tex, level, 6);
|
|
||||||
|
|
||||||
for (face = 0; face < 6; face++) {
|
|
||||||
unsigned x = initial_offsets[face][0] * nblocks;
|
|
||||||
unsigned y = initial_offsets[face][1] * nblocks;
|
|
||||||
unsigned d = nblocks;
|
|
||||||
|
|
||||||
for (level = 0; level <= pt->last_level; level++) {
|
|
||||||
i915_texture_set_image_offset(tex, level, face, x, y);
|
|
||||||
d >>= 1;
|
|
||||||
x += step_offsets[face][0] * d;
|
|
||||||
y += step_offsets[face][1] * d;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
static boolean
|
static boolean
|
||||||
i915_texture_layout(struct i915_texture * tex)
|
i915_texture_layout(struct i915_texture * tex)
|
||||||
{
|
{
|
||||||
|
|
@ -346,7 +362,7 @@ i915_texture_layout(struct i915_texture * tex)
|
||||||
i915_texture_layout_3d(tex);
|
i915_texture_layout_3d(tex);
|
||||||
break;
|
break;
|
||||||
case PIPE_TEXTURE_CUBE:
|
case PIPE_TEXTURE_CUBE:
|
||||||
i915_texture_layout_cube(tex);
|
i9x5_texture_layout_cube(tex);
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
assert(0);
|
assert(0);
|
||||||
|
|
@ -484,93 +500,94 @@ static void
|
||||||
i945_texture_layout_cube(struct i915_texture *tex)
|
i945_texture_layout_cube(struct i915_texture *tex)
|
||||||
{
|
{
|
||||||
struct pipe_resource *pt = &tex->b.b;
|
struct pipe_resource *pt = &tex->b.b;
|
||||||
unsigned level;
|
|
||||||
const unsigned nblocks = util_format_get_nblocksx(pt->format, pt->width0);
|
const unsigned nblocks = util_format_get_nblocksx(pt->format, pt->width0);
|
||||||
|
const unsigned dim = pt->width0;
|
||||||
|
unsigned level;
|
||||||
unsigned face;
|
unsigned face;
|
||||||
|
|
||||||
/*
|
|
||||||
printf("%s %i, %i\n", __FUNCTION__, pt->width0, pt->height0);
|
|
||||||
*/
|
|
||||||
|
|
||||||
assert(pt->width0 == pt->height0); /* cubemap images are square */
|
assert(pt->width0 == pt->height0); /* cubemap images are square */
|
||||||
|
assert(util_next_power_of_two(pt->width0) == pt->width0); /* npot only */
|
||||||
|
assert(util_format_is_s3tc(pt->format)); /* compressed only */
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* XXX Should only be used for compressed formats. But lets
|
|
||||||
* keep this code active just in case.
|
|
||||||
*
|
|
||||||
* Depending on the size of the largest images, pitch can be
|
* Depending on the size of the largest images, pitch can be
|
||||||
* determined either by the old-style packing of cubemap faces,
|
* determined either by the old-style packing of cubemap faces,
|
||||||
* or the final row of 4x4, 2x2 and 1x1 faces below this.
|
* or the final row of 4x4, 2x2 and 1x1 faces below this.
|
||||||
|
*
|
||||||
|
* 64 * 2 / 4 = 32
|
||||||
|
* 14 * 2 = 28
|
||||||
*/
|
*/
|
||||||
if (nblocks > 32)
|
if (pt->width0 >= 64)
|
||||||
tex->stride = align(nblocks * util_format_get_blocksize(pt->format) * 2, 4);
|
tex->stride = nblocks * 2 * util_format_get_blocksize(pt->format);
|
||||||
else
|
else
|
||||||
tex->stride = 14 * 8 * util_format_get_blocksize(pt->format);
|
tex->stride = 14 * 2 * util_format_get_blocksize(pt->format);
|
||||||
|
|
||||||
tex->total_nblocksy = nblocks * 4;
|
/*
|
||||||
|
* Something similary apply for height as well.
|
||||||
|
*/
|
||||||
|
if (pt->width0 >= 4)
|
||||||
|
tex->total_nblocksy = nblocks * 4 + 1;
|
||||||
|
else
|
||||||
|
tex->total_nblocksy = 1;
|
||||||
|
|
||||||
/* Set all the levels to effectively occupy the whole rectangular region.
|
/* Set all the levels to effectively occupy the whole rectangular region */
|
||||||
*/
|
|
||||||
for (level = 0; level <= pt->last_level; level++)
|
for (level = 0; level <= pt->last_level; level++)
|
||||||
i915_texture_set_level_info(tex, level, 6);
|
i915_texture_set_level_info(tex, level, 6);
|
||||||
|
|
||||||
for (face = 0; face < 6; face++) {
|
for (face = 0; face < 6; face++) {
|
||||||
unsigned x = initial_offsets[face][0] * nblocks;
|
/* all calculations in pixels */
|
||||||
unsigned y = initial_offsets[face][1] * nblocks;
|
unsigned total_height = tex->total_nblocksy * 4;
|
||||||
unsigned d = nblocks;
|
unsigned x = initial_offsets[face][0] * dim;
|
||||||
|
unsigned y = initial_offsets[face][1] * dim;
|
||||||
|
unsigned d = dim;
|
||||||
|
|
||||||
#if 0 /* Fix and enable this code for compressed formats */
|
if (dim == 4 && face >= 4) {
|
||||||
if (nblocks == 4 && face >= 4) {
|
|
||||||
y = tex->total_height - 4;
|
|
||||||
x = (face - 4) * 8;
|
x = (face - 4) * 8;
|
||||||
}
|
y = tex->total_nblocksy * 4 - 4; /* 4 = 1 block */
|
||||||
else if (nblocks < 4 && (face > 0)) {
|
} else if (dim < 4 && (face > 0)) {
|
||||||
y = tex->total_height - 4;
|
|
||||||
x = face * 8;
|
x = face * 8;
|
||||||
|
y = total_height - 4;
|
||||||
}
|
}
|
||||||
#endif
|
|
||||||
|
|
||||||
for (level = 0; level <= pt->last_level; level++) {
|
for (level = 0; level <= pt->last_level; level++) {
|
||||||
i915_texture_set_image_offset(tex, level, face, x, y);
|
i915_texture_set_image_offset(tex, level, face,
|
||||||
|
util_format_get_nblocksx(pt->format, x),
|
||||||
|
util_format_get_nblocksy(pt->format, y));
|
||||||
|
|
||||||
d >>= 1;
|
d >>= 1;
|
||||||
|
|
||||||
#if 0 /* Fix and enable this code for compressed formats */
|
|
||||||
switch (d) {
|
switch (d) {
|
||||||
case 4:
|
case 4:
|
||||||
switch (face) {
|
switch (face) {
|
||||||
case PIPE_TEX_FACE_POS_X:
|
case PIPE_TEX_FACE_POS_X:
|
||||||
case PIPE_TEX_FACE_NEG_X:
|
case PIPE_TEX_FACE_NEG_X:
|
||||||
x += step_offsets[face][0] * d;
|
|
||||||
y += step_offsets[face][1] * d;
|
|
||||||
break;
|
|
||||||
case PIPE_TEX_FACE_POS_Y:
|
|
||||||
case PIPE_TEX_FACE_NEG_Y:
|
|
||||||
y += 12;
|
|
||||||
x -= 8;
|
|
||||||
break;
|
|
||||||
case PIPE_TEX_FACE_POS_Z:
|
|
||||||
case PIPE_TEX_FACE_NEG_Z:
|
|
||||||
y = tex->total_height - 4;
|
|
||||||
x = (face - 4) * 8;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
case 2:
|
|
||||||
y = tex->total_height - 4;
|
|
||||||
x = 16 + face * 8;
|
|
||||||
break;
|
|
||||||
|
|
||||||
case 1:
|
|
||||||
x += 48;
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
#endif
|
|
||||||
x += step_offsets[face][0] * d;
|
x += step_offsets[face][0] * d;
|
||||||
y += step_offsets[face][1] * d;
|
y += step_offsets[face][1] * d;
|
||||||
#if 0
|
|
||||||
break;
|
break;
|
||||||
|
case PIPE_TEX_FACE_POS_Y:
|
||||||
|
case PIPE_TEX_FACE_NEG_Y:
|
||||||
|
y += 12;
|
||||||
|
x -= 8;
|
||||||
|
break;
|
||||||
|
case PIPE_TEX_FACE_POS_Z:
|
||||||
|
case PIPE_TEX_FACE_NEG_Z:
|
||||||
|
y = total_height - 4;
|
||||||
|
x = (face - 4) * 8;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case 2:
|
||||||
|
y = total_height - 4;
|
||||||
|
x = bottom_offsets[face];
|
||||||
|
break;
|
||||||
|
case 1:
|
||||||
|
x += 48;
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
x += step_offsets[face][0] * d;
|
||||||
|
y += step_offsets[face][1] * d;
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
#endif
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -590,7 +607,10 @@ i945_texture_layout(struct i915_texture * tex)
|
||||||
i945_texture_layout_3d(tex);
|
i945_texture_layout_3d(tex);
|
||||||
break;
|
break;
|
||||||
case PIPE_TEXTURE_CUBE:
|
case PIPE_TEXTURE_CUBE:
|
||||||
i945_texture_layout_cube(tex);
|
if (!util_format_is_s3tc(pt->format))
|
||||||
|
i9x5_texture_layout_cube(tex);
|
||||||
|
else
|
||||||
|
i945_texture_layout_cube(tex);
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
assert(0);
|
assert(0);
|
||||||
|
|
|
||||||
Loading…
Add table
Reference in a new issue