| @@ -99,6 +99,7 @@ static const struct dri_extension card_extensions[] = { | |||
| {"GL_ARB_depth_clamp", NULL}, | |||
| {"GL_ARB_depth_texture", NULL}, | |||
| {"GL_ARB_fragment_program", NULL}, | |||
| {"GL_ARB_fragment_program_shadow", NULL}, | |||
| {"GL_ARB_occlusion_query", GL_ARB_occlusion_query_functions}, | |||
| {"GL_ARB_multitexture", NULL}, | |||
| {"GL_ARB_point_parameters", GL_ARB_point_parameters_functions}, | |||
| @@ -163,6 +164,7 @@ static const struct dri_extension gl_20_extension[] = { | |||
| #else | |||
| {"GL_VERSION_2_0", GL_VERSION_2_0_functions }, | |||
| #endif /* R600_ENABLE_GLSL_TEST */ | |||
| {NULL, NULL} | |||
| }; | |||
| static const struct tnl_pipeline_stage *r600_pipeline[] = { | |||
| @@ -626,6 +626,31 @@ static GLboolean r600GetTexFormat(struct gl_texture_object *tObj, gl_format mesa | |||
| return GL_TRUE; | |||
| } | |||
| static GLuint r600_translate_shadow_func(GLenum func) | |||
| { | |||
| switch (func) { | |||
| case GL_NEVER: | |||
| return SQ_TEX_DEPTH_COMPARE_NEVER; | |||
| case GL_LESS: | |||
| return SQ_TEX_DEPTH_COMPARE_LESS; | |||
| case GL_LEQUAL: | |||
| return SQ_TEX_DEPTH_COMPARE_LESSEQUAL; | |||
| case GL_GREATER: | |||
| return SQ_TEX_DEPTH_COMPARE_GREATER; | |||
| case GL_GEQUAL: | |||
| return SQ_TEX_DEPTH_COMPARE_GREATEREQUAL; | |||
| case GL_NOTEQUAL: | |||
| return SQ_TEX_DEPTH_COMPARE_NOTEQUAL; | |||
| case GL_EQUAL: | |||
| return SQ_TEX_DEPTH_COMPARE_EQUAL; | |||
| case GL_ALWAYS: | |||
| return SQ_TEX_DEPTH_COMPARE_ALWAYS; | |||
| default: | |||
| WARN_ONCE("Unknown shadow compare function! %d", func); | |||
| return 0; | |||
| } | |||
| } | |||
| void r600SetDepthTexMode(struct gl_texture_object *tObj) | |||
| { | |||
| radeonTexObjPtr t; | |||
| @@ -711,6 +736,15 @@ static void setup_hardware_state(context_t *rmesa, struct gl_texture_object *tex | |||
| SETfield(t->SQ_TEX_RESOURCE4, 0, BASE_LEVEL_shift, BASE_LEVEL_mask); | |||
| SETfield(t->SQ_TEX_RESOURCE5, t->maxLod - t->minLod, LAST_LEVEL_shift, LAST_LEVEL_mask); | |||
| } | |||
| if(texObj->CompareMode == GL_COMPARE_R_TO_TEXTURE_ARB) | |||
| { | |||
| SETfield(t->SQ_TEX_SAMPLER0, r600_translate_shadow_func(texObj->CompareFunc), DEPTH_COMPARE_FUNCTION_shift, DEPTH_COMPARE_FUNCTION_mask); | |||
| } | |||
| else | |||
| { | |||
| CLEARfield(t->SQ_TEX_SAMPLER0, DEPTH_COMPARE_FUNCTION_mask); | |||
| } | |||
| } | |||
| /** | |||
| @@ -4397,7 +4397,10 @@ GLboolean assemble_TEX(r700_AssemblerBase *pAsm) | |||
| pAsm->D.dst.opcode = SQ_TEX_INST_SAMPLE_L; | |||
| break; | |||
| default: | |||
| pAsm->D.dst.opcode = SQ_TEX_INST_SAMPLE; | |||
| if(pAsm->pILInst[pAsm->uiCurInst].TexShadow == 1) | |||
| pAsm->D.dst.opcode = SQ_TEX_INST_SAMPLE_C; | |||
| else | |||
| pAsm->D.dst.opcode = SQ_TEX_INST_SAMPLE; | |||
| } | |||
| pAsm->is_tex = GL_TRUE; | |||
| @@ -4443,11 +4446,46 @@ GLboolean assemble_TEX(r700_AssemblerBase *pAsm) | |||
| pAsm->S[0].src.swizzlew = SQ_SEL_Y; | |||
| } | |||
| if(pAsm->pILInst[pAsm->uiCurInst].TexShadow == 1) | |||
| { | |||
| /* compare value goes to w chan ? */ | |||
| pAsm->S[0].src.swizzlew = SQ_SEL_Z; | |||
| } | |||
| if ( GL_FALSE == next_ins(pAsm) ) | |||
| { | |||
| return GL_FALSE; | |||
| } | |||
| /* add ARB shadow ambient but clamp to 0..1 */ | |||
| if(pAsm->pILInst[pAsm->uiCurInst].TexShadow == 1) | |||
| { | |||
| /* ADD_SAT dst, dst, ambient[texunit] */ | |||
| pAsm->D.dst.opcode = SQ_OP2_INST_ADD; | |||
| if( GL_FALSE == assemble_dst(pAsm) ) | |||
| { | |||
| return GL_FALSE; | |||
| } | |||
| pAsm->D2.dst2.SaturateMode = 1; | |||
| pAsm->S[0].src.rtype = pAsm->D.dst.rtype; | |||
| pAsm->S[0].src.reg = pAsm->D.dst.reg; | |||
| noswizzle_PVSSRC(&(pAsm->S[0].src)); | |||
| noneg_PVSSRC(&(pAsm->S[0].src)); | |||
| pAsm->S[1].src.rtype = SRC_REG_CONSTANT; | |||
| pAsm->S[1].src.reg = pAsm->shadow_regs[pAsm->pILInst[pAsm->uiCurInst].TexSrcUnit]; | |||
| noswizzle_PVSSRC(&(pAsm->S[1].src)); | |||
| noneg_PVSSRC(&(pAsm->S[1].src)); | |||
| if( GL_FALSE == next_ins(pAsm) ) | |||
| { | |||
| return GL_FALSE; | |||
| } | |||
| } | |||
| return GL_TRUE; | |||
| } | |||
| @@ -487,6 +487,8 @@ typedef struct r700_AssemblerBase | |||
| GLuint unVetTexBits; | |||
| GLuint shadow_regs[R700_MAX_TEXTURE_UNITS]; | |||
| } r700_AssemblerBase; | |||
| //Internal use | |||
| @@ -362,8 +362,11 @@ GLboolean r700TranslateFragmentShader(struct r700_fragment_program *fp, | |||
| { | |||
| GLuint number_of_colors_exported; | |||
| GLboolean z_enabled = GL_FALSE; | |||
| GLuint unBit; | |||
| GLuint unBit, shadow_unit; | |||
| int i; | |||
| struct prog_instruction *inst; | |||
| gl_state_index shadow_ambient[STATE_LENGTH] | |||
| = { STATE_INTERNAL, STATE_SHADOW_AMBIENT, 0, 0, 0}; | |||
| //Init_Program | |||
| Init_r700_AssemblerBase( SPT_FP, &(fp->r700AsmCode), &(fp->r700Shader) ); | |||
| @@ -373,6 +376,23 @@ GLboolean r700TranslateFragmentShader(struct r700_fragment_program *fp, | |||
| insert_wpos_code(ctx, mesa_fp); | |||
| } | |||
| /* add/map consts for ARB_shadow_ambient */ | |||
| if(mesa_fp->Base.ShadowSamplers) | |||
| { | |||
| inst = mesa_fp->Base.Instructions; | |||
| for (i = 0; i < mesa_fp->Base.NumInstructions; i++) | |||
| { | |||
| if(inst->TexShadow == 1) | |||
| { | |||
| shadow_unit = inst->TexSrcUnit; | |||
| shadow_ambient[2] = shadow_unit; | |||
| fp->r700AsmCode.shadow_regs[shadow_unit] = | |||
| _mesa_add_state_reference(mesa_fp->Base.Parameters, shadow_ambient); | |||
| } | |||
| inst++; | |||
| } | |||
| } | |||
| Map_Fragment_Program(&(fp->r700AsmCode), mesa_fp, ctx); | |||
| if( GL_FALSE == Find_Instruction_Dependencies_fp(fp, mesa_fp) ) | |||