Added fixes for filter modes and support for anisotropy filters.
authorAapo Tahkola <aet@rasterburn.org>
Fri, 14 Jan 2005 21:53:00 +0000 (21:53 +0000)
committerAapo Tahkola <aet@rasterburn.org>
Fri, 14 Jan 2005 21:53:00 +0000 (21:53 +0000)
Wrap modes would work perfectly but i messed up something when cleaning up
the code :/ Border color code is incomplete because i forgot to check how to
set border size :)

src/mesa/drivers/dri/r300/r300_cmdbuf.c
src/mesa/drivers/dri/r300/r300_context.h
src/mesa/drivers/dri/r300/r300_reg.h
src/mesa/drivers/dri/r300/r300_state.c
src/mesa/drivers/dri/r300/r300_tex.c

index 3d8f4e9711872f15b92cf24c91b11015cfb23429..92f107b9db912233dab7f98fde89b348bed92aaf 100644 (file)
@@ -452,6 +452,9 @@ void r300InitCmdBuf(r300ContextPtr r300)
                
        ALLOC_STATE( tex.unknown5, variable, mtu+1, "tex_unknown5", 0 );
                r300->hw.tex.unknown5.cmd[R300_TEX_CMD_0] = cmducs(R300_TX_UNK5_0, 0);
+               
+       ALLOC_STATE( tex.border_color, variable, mtu+1, "tex_border_color", 0 );
+               r300->hw.tex.border_color.cmd[R300_TEX_CMD_0] = cmducs(R300_TX_BORDER_COLOR_0, 0);
        
 
        /* Setup the atom linked list */
@@ -531,6 +534,7 @@ void r300InitCmdBuf(r300ContextPtr r300)
        insert_at_tail(&r300->hw.atomlist, &r300->hw.tex.offset);
        insert_at_tail(&r300->hw.atomlist, &r300->hw.tex.unknown4);
        insert_at_tail(&r300->hw.atomlist, &r300->hw.tex.unknown5);
+       insert_at_tail(&r300->hw.atomlist, &r300->hw.tex.border_color);
 
        r300->hw.is_dirty = GL_TRUE;
        r300->hw.all_dirty = GL_TRUE;
index a561f31118ee97664059dd648f186c779638d593..6a7427b168b1e2166da0b5a6f5f53bd8c8bc90b3 100644 (file)
@@ -441,7 +441,8 @@ struct r300_hw_state {
                struct r300_state_atom format;
                struct r300_state_atom offset;
                struct r300_state_atom unknown4;
-               struct r300_state_atom unknown5;                
+               struct r300_state_atom unknown5;
+               struct r300_state_atom border_color;
                } tex;
        struct r300_state_atom txe;     /* tex enable (4104) */
 };
index d701ccc2f462fd86c90df2971504fd0b8f3ad921..1244579964a1e1887b3b0c98298ddc62e9ab3758 100644 (file)
@@ -565,31 +565,44 @@ I am fairly certain that they are correct unless stated otherwise in comments.
 // TX_OFFSET_0 + (4*N) */
 #define R300_TX_FILTER_0                    0x4400
 #       define R300_TX_REPEAT                    0
-#       define R300_TX_CLAMP_TO_EDGE             1
-#       define R300_TX_CLAMP                     2
-#       define R300_TX_CLAMP_TO_BORDER           3
-
-#       define R300_TX_WRAP_S_SHIFT              1
-#       define R300_TX_WRAP_S_MASK               (3 << 1)
-#       define R300_TX_WRAP_T_SHIFT              4
-#       define R300_TX_WRAP_T_MASK               (3 << 4)
+#       define R300_TX_MIRRORED                  1
+#       define R300_TX_CLAMP                     4
+#       define R300_TX_CLAMP_TO_EDGE             2
+#       define R300_TX_CLAMP_TO_BORDER           6
+#       define R300_TX_WRAP_S_SHIFT              0
+#       define R300_TX_WRAP_S_MASK               (7 << 0)
+#       define R300_TX_WRAP_T_SHIFT              3
+#       define R300_TX_WRAP_T_MASK               (7 << 3)
+#       define R300_TX_WRAP_Q_SHIFT              6
+#       define R300_TX_WRAP_Q_MASK               (7 << 6)
 #       define R300_TX_MAG_FILTER_NEAREST        (1 << 9)
 #       define R300_TX_MAG_FILTER_LINEAR         (2 << 9)
 #       define R300_TX_MAG_FILTER_MASK           (3 << 9)
 #       define R300_TX_MIN_FILTER_NEAREST        (1 << 11)
 #       define R300_TX_MIN_FILTER_LINEAR         (2 << 11)
-/* TODO: Test and verify R300_TX_MIN_FILTER_MASK */
-#      define R300_TX_MIN_FILTER_NEAREST_MIP_NEAREST       (2  <<  12)
-#      define R300_TX_MIN_FILTER_NEAREST_MIP_LINEAR        (3  <<  12)
-#      define R300_TX_MIN_FILTER_LINEAR_MIP_NEAREST        (6  <<  12)
-#      define R300_TX_MIN_FILTER_LINEAR_MIP_LINEAR         (7  <<  12)
-#      define R300_TX_MIN_FILTER_ANISO_NEAREST             (8  <<  12)
-#      define R300_TX_MIN_FILTER_ANISO_LINEAR              (9  <<  12)
-#      define R300_TX_MIN_FILTER_ANISO_NEAREST_MIP_NEAREST (10 <<  12)
-#      define R300_TX_MIN_FILTER_ANISO_NEAREST_MIP_LINEAR  (11 <<  12)
-
-#       define R300_TX_MIN_FILTER_MASK           (0x0000f800)
+#      define R300_TX_MIN_FILTER_NEAREST_MIP_NEAREST       (5  <<  11)
+#      define R300_TX_MIN_FILTER_NEAREST_MIP_LINEAR        (9  <<  11)
+#      define R300_TX_MIN_FILTER_LINEAR_MIP_NEAREST        (6  <<  11)
+#      define R300_TX_MIN_FILTER_LINEAR_MIP_LINEAR         (10 <<  11)
+
+/* NOTE: NEAREST doesnt seem to exist.
+   Im not seting MAG_FILTER_MASK and (3 << 11) on for all
+   anisotropy modes because that would void selected mag filter */
+#      define R300_TX_MIN_FILTER_ANISO_NEAREST             ((0 << 13) /*|R300_TX_MAG_FILTER_MASK|(3<<11)*/)
+#      define R300_TX_MIN_FILTER_ANISO_LINEAR              ((0 << 13) /*|R300_TX_MAG_FILTER_MASK|(3<<11)*/)
+#      define R300_TX_MIN_FILTER_ANISO_NEAREST_MIP_NEAREST ((1 << 13) /*|R300_TX_MAG_FILTER_MASK|(3<<11)*/)
+#      define R300_TX_MIN_FILTER_ANISO_NEAREST_MIP_LINEAR  ((2 << 13) /*|R300_TX_MAG_FILTER_MASK|(3<<11)*/)
+#       define R300_TX_MIN_FILTER_MASK           ( (15 << 11) | (3 << 13) )
+#      define R300_TX_MAX_ANISO_1_TO_1  (0 << 21)
+#      define R300_TX_MAX_ANISO_2_TO_1  (2 << 21)
+#      define R300_TX_MAX_ANISO_4_TO_1  (4 << 21)
+#      define R300_TX_MAX_ANISO_8_TO_1  (6 << 21)
+#      define R300_TX_MAX_ANISO_16_TO_1 (8 << 21)
+#      define R300_TX_MAX_ANISO_MASK    (14 << 21)
+
 #define R300_TX_UNK1_0                      0x4440
+#      define R300_LOD_BIAS_MASK           0x1fff
+
 #define R300_TX_SIZE_0                      0x4480
 #       define R300_TX_WIDTHMASK_SHIFT           0
 #       define R300_TX_WIDTHMASK_MASK            (2047 << 0)
@@ -684,6 +697,8 @@ I am fairly certain that they are correct unless stated otherwise in comments.
 /* END */
 #define R300_TX_UNK4_0                      0x4580
 #define R300_TX_UNK5_0                      0x45C0
+#define R300_TX_BORDER_COLOR_0              0x45F0 //ff00ff00 == { 0, 1.0, 0, 1.0 }
+
 /* END */
 
 /* BEGIN: Fragment program instruction set
index 56dad7c0cfc5da92a71a0cbc62751a08a5e12cab..652418af6abc33e3b4010407f42e652a724cf0f8 100644 (file)
@@ -983,6 +983,7 @@ void r300_setup_textures(GLcontext *ctx)
        R300_STATECHANGE(r300, tex.offset);
        R300_STATECHANGE(r300, tex.unknown4);
        R300_STATECHANGE(r300, tex.unknown5);
+       R300_STATECHANGE(r300, tex.border_color);
        
        r300->state.texture.tc_count=0;
        
@@ -1011,10 +1012,12 @@ void r300_setup_textures(GLcontext *ctx)
                        max_texture_unit=i;
                        r300->hw.txe.cmd[R300_TXE_ENABLE]|=(1<<i);
                        
-                       r300->hw.tex.filter.cmd[R300_TEX_VALUE_0+i]=t->filter;
+                       /* Turn off rest of the bits that are wrong. Im going to get rid of this soon, dont worry :) */
+                       t->filter &= R300_TX_MIN_FILTER_MASK | R300_TX_MAG_FILTER_MASK
+                                       |R300_TX_WRAP_S_MASK | R300_TX_WRAP_T_MASK |
+                                       R300_TX_WRAP_Q_MASK | R300_TX_MAX_ANISO_MASK;
                        
-                       /* Turn off rest of the bits that are wrong */
-                       t->filter &= R300_TX_MIN_FILTER_MASK | R300_TX_MAG_FILTER_MASK;
+                       r300->hw.tex.filter.cmd[R300_TEX_VALUE_0+i]=t->filter;
                        
                        /* No idea why linear filtered textures shake when puting random data */
                        /*r300->hw.tex.unknown1.cmd[R300_TEX_VALUE_0+i]=(rand()%0xffffffff) & (~0x1fff);*/
@@ -1023,6 +1026,7 @@ void r300_setup_textures(GLcontext *ctx)
                        r300->hw.tex.offset.cmd[R300_TEX_VALUE_0+i]=r300->radeon.radeonScreen->fbLocation+t->offset;
                        r300->hw.tex.unknown4.cmd[R300_TEX_VALUE_0+i]=0x0;
                        r300->hw.tex.unknown5.cmd[R300_TEX_VALUE_0+i]=0x0;
+                       r300->hw.tex.border_color.cmd[R300_TEX_VALUE_0+i]=t->pp_border_color;
 
                        /* We don't know how to set this yet */
                        //value from r300_lib.c for RGB24
@@ -1096,6 +1100,7 @@ void r300_setup_textures(GLcontext *ctx)
        ((drm_r300_cmd_header_t*)r300->hw.tex.offset.cmd)->unchecked_state.count = max_texture_unit+1;
        ((drm_r300_cmd_header_t*)r300->hw.tex.unknown4.cmd)->unchecked_state.count = max_texture_unit+1;
        ((drm_r300_cmd_header_t*)r300->hw.tex.unknown5.cmd)->unchecked_state.count = max_texture_unit+1;
+       ((drm_r300_cmd_header_t*)r300->hw.tex.border_color.cmd)->unchecked_state.count = max_texture_unit+1;
        
        if (RADEON_DEBUG & DEBUG_STATE)
                fprintf(stderr, "TX_ENABLE: %08x  max_texture_unit=%d\n", r300->hw.txe.cmd[R300_TXE_ENABLE], max_texture_unit);
index 33a8fa1e5ca2022816768f349d7c3280e1c29f59..884d42cf472d6dd6233a2912a1c1fec2caeeecea 100644 (file)
@@ -60,46 +60,42 @@ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
  * \param swrap Wrap mode for the \a s texture coordinate
  * \param twrap Wrap mode for the \a t texture coordinate
  */
-
 static void r300SetTexWrap(r300TexObjPtr t, GLenum swrap, GLenum twrap,
                           GLenum rwrap)
 {
        GLboolean is_clamp = GL_FALSE;
-       GLboolean is_clamp_to_border = GL_FALSE;
-       
-/* Most of these seem to be incorrect so disable for now */
-#if 0  
+       unsigned long hw_swrap=0, hw_twrap=0, hw_qwrap=0;
+                       
        t->filter &=
-           ~(R200_CLAMP_S_MASK | R200_CLAMP_T_MASK | R200_BORDER_MODE_D3D);
-
+           ~(R300_TX_WRAP_S_MASK | R300_TX_WRAP_T_MASK | R300_TX_WRAP_Q_MASK);
+       
        switch (swrap) {
        case GL_REPEAT:
-               t->filter |= R200_CLAMP_S_WRAP;
+               hw_swrap |= R300_TX_REPEAT;
                break;
        case GL_CLAMP:
-               t->filter |= R200_CLAMP_S_CLAMP_GL;
+               hw_swrap |= R300_TX_CLAMP;
                is_clamp = GL_TRUE;
                break;
        case GL_CLAMP_TO_EDGE:
-               t->filter |= R200_CLAMP_S_CLAMP_LAST;
+               hw_swrap |= R300_TX_CLAMP_TO_EDGE;
                break;
        case GL_CLAMP_TO_BORDER:
-               t->filter |= R200_CLAMP_S_CLAMP_GL;
-               is_clamp_to_border = GL_TRUE;
+               hw_swrap |= R300_TX_CLAMP_TO_BORDER;
                break;
        case GL_MIRRORED_REPEAT:
-               t->filter |= R200_CLAMP_S_MIRROR;
+               hw_swrap |= R300_TX_REPEAT | R300_TX_MIRRORED;
                break;
        case GL_MIRROR_CLAMP_EXT:
-               t->filter |= R200_CLAMP_S_MIRROR_CLAMP_GL;
+               hw_swrap |= R300_TX_CLAMP | R300_TX_MIRRORED;
                is_clamp = GL_TRUE;
                break;
        case GL_MIRROR_CLAMP_TO_EDGE_EXT:
-               t->filter |= R200_CLAMP_S_MIRROR_CLAMP_LAST;
+               hw_swrap |= R300_TX_CLAMP_TO_EDGE | R300_TX_MIRRORED;
                break;
        case GL_MIRROR_CLAMP_TO_BORDER_EXT:
-               t->filter |= R200_CLAMP_S_MIRROR_CLAMP_GL;
-               is_clamp_to_border = GL_TRUE;
+               hw_swrap |= R300_TX_CLAMP_TO_BORDER | R300_TX_MIRRORED;
                break;
        default:
                _mesa_problem(NULL, "bad S wrap mode in %s", __FUNCTION__);
@@ -107,76 +103,72 @@ static void r300SetTexWrap(r300TexObjPtr t, GLenum swrap, GLenum twrap,
 
        switch (twrap) {
        case GL_REPEAT:
-               t->filter |= R200_CLAMP_T_WRAP;
+               hw_twrap |= R300_TX_REPEAT;
                break;
        case GL_CLAMP:
-               t->filter |= R200_CLAMP_T_CLAMP_GL;
+               hw_twrap |= R300_TX_CLAMP;
                is_clamp = GL_TRUE;
                break;
        case GL_CLAMP_TO_EDGE:
-               t->filter |= R200_CLAMP_T_CLAMP_LAST;
+               hw_twrap |= R300_TX_CLAMP_TO_EDGE;
                break;
        case GL_CLAMP_TO_BORDER:
-               t->filter |= R200_CLAMP_T_CLAMP_GL | R200_BORDER_MODE_D3D;
-               is_clamp_to_border = GL_TRUE;
+               hw_twrap |= R300_TX_CLAMP_TO_BORDER;
                break;
        case GL_MIRRORED_REPEAT:
-               t->filter |= R200_CLAMP_T_MIRROR;
+               hw_twrap |= R300_TX_REPEAT | R300_TX_MIRRORED;
                break;
        case GL_MIRROR_CLAMP_EXT:
-               t->filter |= R200_CLAMP_T_MIRROR_CLAMP_GL;
+               hw_twrap |= R300_TX_CLAMP | R300_TX_MIRRORED;
                is_clamp = GL_TRUE;
                break;
        case GL_MIRROR_CLAMP_TO_EDGE_EXT:
-               t->filter |= R200_CLAMP_T_MIRROR_CLAMP_LAST;
+               hw_twrap |= R300_TX_CLAMP_TO_EDGE | R300_TX_MIRRORED;
                break;
        case GL_MIRROR_CLAMP_TO_BORDER_EXT:
-               t->filter |= R200_CLAMP_T_MIRROR_CLAMP_GL;
-               is_clamp_to_border = GL_TRUE;
+               hw_twrap |= R300_TX_CLAMP_TO_BORDER | R300_TX_MIRRORED;
                break;
        default:
                _mesa_problem(NULL, "bad T wrap mode in %s", __FUNCTION__);
        }
 
-       t->format_x &= ~R200_CLAMP_Q_MASK;
-
        switch (rwrap) {
        case GL_REPEAT:
-               t->format_x |= R200_CLAMP_Q_WRAP;
+               hw_qwrap |= R300_TX_REPEAT;
                break;
        case GL_CLAMP:
-               t->format_x |= R200_CLAMP_Q_CLAMP_GL;
+               hw_qwrap |= R300_TX_CLAMP;
                is_clamp = GL_TRUE;
                break;
        case GL_CLAMP_TO_EDGE:
-               t->format_x |= R200_CLAMP_Q_CLAMP_LAST;
+               hw_qwrap |= R300_TX_CLAMP_TO_EDGE;
                break;
        case GL_CLAMP_TO_BORDER:
-               t->format_x |= R200_CLAMP_Q_CLAMP_GL;
-               is_clamp_to_border = GL_TRUE;
+               hw_qwrap |= R300_TX_CLAMP_TO_BORDER;
                break;
        case GL_MIRRORED_REPEAT:
-               t->format_x |= R200_CLAMP_Q_MIRROR;
+               hw_qwrap |= R300_TX_REPEAT | R300_TX_MIRRORED;
                break;
        case GL_MIRROR_CLAMP_EXT:
-               t->format_x |= R200_CLAMP_Q_MIRROR_CLAMP_GL;
+               hw_qwrap |= R300_TX_CLAMP | R300_TX_MIRRORED;
                is_clamp = GL_TRUE;
                break;
        case GL_MIRROR_CLAMP_TO_EDGE_EXT:
-               t->format_x |= R200_CLAMP_Q_MIRROR_CLAMP_LAST;
+               hw_qwrap |= R300_TX_CLAMP_TO_EDGE | R300_TX_MIRRORED;
                break;
        case GL_MIRROR_CLAMP_TO_BORDER_EXT:
-               t->format_x |= R200_CLAMP_Q_MIRROR_CLAMP_GL;
-               is_clamp_to_border = GL_TRUE;
+               hw_qwrap |= R300_TX_CLAMP_TO_BORDER | R300_TX_MIRRORED;
                break;
        default:
                _mesa_problem(NULL, "bad R wrap mode in %s", __FUNCTION__);
        }
        
-       if (is_clamp_to_border) {
-               t->filter |= R200_BORDER_MODE_D3D;
-       }
-
+       t->filter |= hw_swrap << R300_TX_WRAP_S_SHIFT;
+       t->filter |= hw_twrap << R300_TX_WRAP_T_SHIFT;
+       t->filter |= hw_qwrap << R300_TX_WRAP_Q_SHIFT;
+       
+#if 0
+       t->format_x &= ~R200_CLAMP_Q_MASK;
        t->border_fallback = (is_clamp && is_clamp_to_border);
 #endif 
 }
@@ -184,22 +176,19 @@ static void r300SetTexWrap(r300TexObjPtr t, GLenum swrap, GLenum twrap,
 static void r300SetTexMaxAnisotropy(r300TexObjPtr t, GLfloat max)
 {
        
-/* Needs testing */    
-#if 0  
-       t->filter &= ~R200_MAX_ANISO_MASK;
+       t->filter &= ~R300_TX_MAX_ANISO_MASK;
 
        if (max == 1.0) {
-               t->filter |= R200_MAX_ANISO_1_TO_1;
+               t->filter |= R300_TX_MAX_ANISO_1_TO_1;
        } else if (max <= 2.0) {
-               t->filter |= R200_MAX_ANISO_2_TO_1;
+               t->filter |= R300_TX_MAX_ANISO_2_TO_1;
        } else if (max <= 4.0) {
-               t->filter |= R200_MAX_ANISO_4_TO_1;
+               t->filter |= R300_TX_MAX_ANISO_4_TO_1;
        } else if (max <= 8.0) {
-               t->filter |= R200_MAX_ANISO_8_TO_1;
+               t->filter |= R300_TX_MAX_ANISO_8_TO_1;
        } else {
-               t->filter |= R200_MAX_ANISO_16_TO_1;
+               t->filter |= R300_TX_MAX_ANISO_16_TO_1;
        }
-#endif 
 }
 
 /**
@@ -212,14 +201,14 @@ static void r300SetTexMaxAnisotropy(r300TexObjPtr t, GLfloat max)
 
 static void r300SetTexFilter(r300TexObjPtr t, GLenum minf, GLenum magf)
 {
-       GLuint anisotropy = 0; //(t->filter & R200_MAX_ANISO_MASK);
+       GLuint anisotropy = (t->filter & R300_TX_MAX_ANISO_MASK);
 
        t->filter &= ~(R300_TX_MIN_FILTER_MASK | R300_TX_MAG_FILTER_MASK);
 #if 0  
        //t->format_x &= ~R200_VOLUME_FILTER_MASK;
 #endif 
        
-       if (anisotropy == R200_MAX_ANISO_1_TO_1) {
+       if (anisotropy == R300_TX_MAX_ANISO_1_TO_1) {
                switch (minf) {
                case GL_NEAREST:
                        t->filter |= R300_TX_MIN_FILTER_NEAREST;
@@ -836,7 +825,7 @@ static void r300TexEnv(GLcontext * ctx, GLenum target,
                        GLfloat bias, min;
                        GLuint b;
 
-                       /* The R200's LOD bias is a signed 2's complement value with a
+                       /* The R300's LOD bias is a signed 2's complement value with a
                         * range of -16.0 <= bias < 16.0.
                         *
                         * NOTE: Add a small bias to the bias for conform mipsel.c test.
@@ -847,13 +836,9 @@ static void r300TexEnv(GLcontext * ctx, GLenum target,
                                            "no_neg_lod_bias") ? 0.0 : -16.0;
                        bias = CLAMP(bias, min, 16.0);
                        
-#define R300_LOD_BIAS_MASK     0x1fff
-                       
-                       /* 1.0 is 0x00000100 and 10.0 is 0x00000a00 --aet */
-
+                       /* 0.0 - 16.0 == 0x0 - 0x1000 */
+                       /* 0.0 - -16.0 == 0x1001 - 0x1fff */
                        b = 0x1000 / 16.0 * bias;
-                       /* No clue about negative biases but this would 
-                          seem logical if positive max is 0x1000 */
                        b &= R300_LOD_BIAS_MASK;
                        
                        if(b != (rmesa->hw.tex.unknown1.cmd[R300_TEX_VALUE_0+unit] & R300_LOD_BIAS_MASK)){